text:
---
title: Making PPXs Portable with ocaml-migrate-parsetree
layout: post
author: let-def
category: Projects
tags: ppx
---

An effort to make PPXs portable across compiler versions.

PPX extensions work by receiving a syntax tree from the compiler, rewriting it, and sending it back. Extensions obtain the definition of the syntax tree as well as some helpers from compiler-libs. Thus they tend to depend on the internal of the compiler.

PPX developers often have to maintain separate code for each version of the compiler they want to support. When a new compiler version is introduced, most opam packages are unavailable because of PPX breakage.

To address these two problems [ocaml-migrate-parsetree](https://github.com/let-def/ocaml-migrate-parsetree) versions the syntax tree and provides conversion functions.
Migrating to a new version always succeeds, migrating to an older version fails if some features in use are not available.

Versions covered are 4.02, 4.03, 4.04 and trunk (4.05). A code working with 4.04 will work out of the box on 4.05. However, if the code later evolves to make use of 4.05 specific features, it will no longer be backwards compatible.

Features provided by `ocaml-migrate-parsetree` includes:
- versioning of `Asttypes`, `Parsetree`, `Ast_helper`, `Outcometree` and parts of `Ast_mapper` and `Docstrings`
- unmarshalling of any supported versions of syntax trees
- conversion of parsetrees and lifting of `Ast_mapper.mapper` between arbitrary versions.

For `Ast_mapper` and `Docstrings`, anything relying on global state has been removed. Lifting of `Ast_mapper.mapper` breaks the open recursion (the Ast is converted to the targeted version only once when entering the mapper and converted back when leaving).

## Minimal guide to porting a PPX extension

Porting is easy as long as you stick to modules that are versioned by _ocaml-migrate-parsetree_. It is trivial if you make direct use of `Ast_mapper`. However using `Ast_mapper_class` from [ppx_tools](https://github.com/alainfrisch/ppx_tools) breaks this approach.

Starting from a PPX written against OCaml 4.04, porting amounts to:

```ocaml
(* Shadowing compiler-libs modules with the ones versioned for 4.04 *)
open Migrate_parsetree
open Ast_404

... (* your ppx code *)

(* ########################################### *)
(* Registering the mapper with the host version of compiler-libs

   Original code:
   let () =
     Ast_mapper.run_main @@ fun _ -> my_mapper
*)

(* Create a module converting structures from 4.04 to current version *)
module To_current = Convert(OCaml_404)(OCaml_current)

let () =
  (* Original Ast_mapper is shadowed.
     Compiler_libs module provides aliase to the original one. *)
  Compiler_libs.Ast_mapper.run_main @@ fun _ ->
  (* Finally lift the mapper *)
  To_current.copy_mapper my_mapper

(* ########################################### *)
(* Alternatively, if the implementation uses Ast_mapper.register:

   let () = Ast_mapper.register "my_mapper" mapper
*)

let () =
  let module To_current = Convert(OCaml_404)(OCaml_current) in
  Compiler_libs.Ast_mapper.register "my_mapper" (To_current.copy_mapper mapper)
```

## Future work

While a few PPX extensions have already been ported, the ones relying on `Ast_mapper_class` are not handled yet. Porting more of them and agreeing on a reasonable set of features to cover most use cases is a prerequisite before a 1.0 release.

Another axis is the handling of unsupported features. As of today, converting an unsupported feature raises an exception. Some PPX extensions could opt-in a softer policy of encoding new constructions as attributes. This make sense when using an old PPX with a new version of the compiler.

repository: ocamllabs/ocamllabs-www

gha_language: CSS

repo_name: ocamllabs/ocamllabs-www


text:
---
breadcrumbs:
- - /chromium-os
  - Chromium OS
page_name: glitch-vulnerability-status
title: GLitch vulnerability status
---

## Vulnerability description

The [GLitch
vulnerability](https://www.vusec.net/wp-content/uploads/2018/05/glitch.pdf) uses
timing information gathered from the GPU to execute a
[Rowhammer-style](https://en.wikipedia.org/wiki/Row_hammer) bit-flip attack.
High-precision GPU timers can be used from an untrusted web page via WebGL to
determine the physical layout of memory pages. GL shaders running on the GPU are
then used to cause bit flips in CPU-accessible DRAM on unified memory
architecture GPUs.

Successful exploitation would enable an attacker to escalate privileges from
Javascript. This has been demonstrated to allow arbitrary code execution within
the Chrome sandbox.

## Chrome OS response

Chrome OS 65, released to the stable channel on [April 5,
2018](https://chromereleases.googleblog.com/2018/04/stable-channel-update-for-chrome-os.html),
mitigates the remote vector of the GLitch vulnerability on all Chrome OS devices
by removing access to high-precision WebGL timers. Users can [enable Site
Isolation](http://www.chromium.org/Home/chromium-security/site-isolation) for
further protection.

## Affected devices

Chrome OS Intel devices are protected against GLitch and other Rowhammer-style
bit flips by either using double refresh; or TRR on DDR4 RAM, if supported.
Chrome OS ARM devices use DDR3 RAM, which is theoretically vulnerable to
Rowhammer-style attacks; however, bit flips have not been reproduced on these
devices. No further action is necessary for Chrome OS ARM devices at the moment.

repository: iridium-browser/iridium-browser

branch_name: refs/heads/master

extension: md

license_type: permissive

repo_name: iridium-browser/iridium-browser


text:
### Active Projects
- [expr-eval](https://github.com/silentmatt/expr-eval) - Mathematical expression evaluator for browsers and Node.
- [expr-eval-cli](https://github.com/silentmatt/expr-eval-cli) - Use expr-eval from the command line.
- [javascript-biginteger](https://github.com/silentmatt/javascript-biginteger) - Arbitrarily-sized integers for JS.

### Other projects
- [DSS](https://github.com/silentmatt/dss) - Dynamic/Dry Style Sheets. Think Less/Sass, but written in Java.

license: MIT


text:
Frequent Itemset Generator
==========================

Introduction
------------

Finds statistically significant sets of frequent items in large datasets. For
example, let's say we have a database of supermarket transactions, or baskets,
each containing a number of grocery items. If we want to find the frequent
grocery items in this database, we're finding the grocery items which are most
frequently purchased together: the "frequent itemsets."

Generally we want the sets of items to occur in
at least m transactions. We'll call this the minimum support number. The minimum
support number allows us to specify how frequent an itemset must be to be
included in the final output - obviously, a set of items that does not occur in
any transactions, or even a small number of transactions, is insignificant to
the user of the system. The minimum support generally must be tuned for each
specific dataset to determine what will give the user plenty of data, but not
so much data that the output becomes unusable.

To this end, we also include the maximum support number, which caps the number
of possible transactions any set in the final output can have. Imagine that at
a specific supermarket, nearly every customer buys milk when they buy anything
else. Then, it is not very significant to include milk in the final output,
since the item is so commonly purchased. Thus we can use the maximum support
to filter out items like this. As with the min support, this number will also
vary wildly between datasets. If you end up using the max support metric (less
than 100% of course) for a dataset,
this indicates that you should probably use the FPGrowth algorithm, as this
algorithm runs much quicker on datasets with a large number of similar items
between transactions.

Use
---

This service was built to find the genetic transcription factors (proteins)
which most frequently occur together in one gene. However, you can add your own
dataset if you want to use it for a different purpose.

Customizability
---------------

 - class BasketIterator: Implement BasketIterator to create your own dataset.
 - class ItemsetGenerator: Implement ItemsetGenerator to create your own
 algorithm.
 - file lib/passwd.groovy: Password file - holds database configuration info.

API Reference
-------------

 - Get request: `get [minSup:decimal:0-1] [maxSup:decimal:0-1]`
 Returns: `{
    'res': "(SUCCESS | FAILURE)":string,
    'item-cnt': "integer indicating the number of unique items":integer,
    'reason': "Reason for failure if FAILURE, request type if SUCCESS.":string,
    'message': "Explanation of failure iff 'res' == 'FAILURE'.":string,
    'time': "integer indicating the time it took to find itemsets":integer,
    'data': "map with the itemsets and their frequency counts; ex: [[one, two]: 138]":map
 }'
 Returns a list of the itemsets between the min and max support values.
 'time' is always 0 on FAILURE.
 `maxSup` must be less than `minSup`, obviously. Both are decimal values
 indicating the percent support an itemset must have to be included.

 - Set request: `set [BasketIterator] [ItemsetGenerator]`
 Returns: same as Get request except with no 'data' attribute; 'time'
 will always be 0
 If the request is successful, 'res' will be set to SUCCESS and 'reason'
 will be "SET". Any subsequent queries by client will use the
 BasketIterator and ItemsetGenerator specified.

 Both Set values must be fully-qualified class names.

Two algorithms are available; selectable at runtime:
----------------------------------------------------
 - Apriori algorithm: Iterates through every transaction (supermarket basket)
 and candidate to find the most frequent sets of items. A candidate is any one
 subset of items in the entire set of items (in our example, every item in the
 supermarket). So we start with candidates with one item (Bread, milk, cheese),
 then we look for baskets with two items ([Bread, milk], [milk, cheese],
 [cheese, bread]), and so on until we've searched every subset. At worst case,
 this algorithm is exponential, as there are 2^n subsets for n items. But the
 trick is that we drop from consideration all larger subsets containing an
 infrequent item. For example, if we know that bread is in m - 1 baskets (one
 less than our minimum support) then we know bread is _never_ a frequent item,
 so we can drop [Bread, milk], [cheese, Bread], and [bread, milk, cheese] from
 our consideration. This optimization significantly speeds up the algorithm for
 reasonable minimum support values (if you set the minimum support to 0, every
 item set will be frequent and you'll have to iterate through every set).

 - FPGrowth algorithm: Based on the FPTree data structure. This algorithm builds
 a tree representing your dataset. The more items each transaction has in
 common, the smaller the tree will be and thus the faster this algorithm will
 procese all frequent itemsets.

License
=======

   Copyright 2014 Therin Irwin

   Licensed under the Apache License, Version 2.0 (the "License");
   you may not use this file except in compliance with the License.
   You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.

repository: brovine-developers/freq-itemset-gen

repo_name: brovine-developers/freq-itemset-gen


text:
# Release History

### 0.6.1 (2023-06-06)

#### Bug Fixes

* Don't use self-signed JWT credentials if the global configuration endpoint has been modified

### 0.6.0 (2023-05-31)

#### Features

* Uses binary protobuf definitions for better forward compatibility ([#21680](https://github.com/googleapis/google-cloud-ruby/issues/21680))

### 0.5.0 (2023-03-08)

#### Features

* Support REST transport ([#20630](https://github.com/googleapis/google-cloud-ruby/issues/20630))

### 0.4.0 (2022-07-08)

#### Features

* Updated minimum Ruby version to 2.6 ([#18443](https://github.com/googleapis/google-cloud-ruby/issues/18443))
#### Bug Fixes

* Fixed a crash when making certain long-running-operations status calls ([#18441](https://github.com/googleapis/google-cloud-ruby/issues/18441))

### 0.3.5 / 2022-01-11

#### Bug Fixes

* Honor quota project in auxiliary operations clients

#### Documentation

* Fix titles of documentation pages
* Remove some broken images and fix outdated content in authentication documentation

### 0.3.4 / 2021-11-08

#### Documentation

* Added simple code snippets to RPC method documentation

### 0.3.3 / 2021-08-11

#### Bug Fixes

* Honor client-level timeout configuration

### 0.3.2 / 2021-07-12

#### Documentation

* Clarify some language around authentication configuration

### 0.3.1 / 2021-06-17

#### Bug Fixes

* Support future 1.x versions of gapic-common

### 0.3.0 / 2021-03-08

#### Features

* Drop support for Ruby 2.4 and add support for Ruby 3.0

### 0.2.0 / 2021-02-02

#### Features

* Use self-signed JWT credentials when possible, and support the wait_operation RPC for long-running operations

### 0.1.1 / 2021-01-19

#### Documentation

* Timeout config description correctly gives the units as seconds.

### 0.1.0 / 2020-10-29

Initial release.

repository: googleapis/google-cloud-ruby

branch_name: refs/heads/main

gha_language: Ruby

repo_name: googleapis/google-cloud-ruby


text:
# Title

Transaction Order Dependence

## Relationships

[CWE-362: Concurrent Execution using Shared Resource with Improper Synchronization ('Race Condition')](https://cwe.mitre.org/data/definitions/362.html)

## Description

The Ethereum network processes transactions in blocks, with new blocks getting confirmed approximately every 17 seconds. Miners review the transactions they have received and select which ones to include in a block, based on who has paid a high enough gas price to be included. Additionally, when transactions are sent to the Ethereum network, they are forwarded to each node for processing. Thus, a person who is running an Ethereum node can tell which transactions are going to occur before they are finalized. A race condition vulnerability occurs when code depends on the order of the transactions submitted to it.

The simplest example of a race condition is when a smart contract gives a reward for submitting information. Suppose a contract will give out 1 token to the first person who solves a math problem. Alice solves the problem and submits the answer to the network with a standard gas price. Eve runs an Ethereum node and can see the answer to the math problem in the transaction that Alice submitted to the network. So, Eve submits the answer to the network with a much higher gas price, and thus it gets processed and committed before Alice's transaction. Eve receives one token, and Alice gets nothing, even though it was Alice who worked to solve the problem. A common way this occurs in practice is when a contract rewards people for calling out bad behavior in a protocol by giving a bad actor's deposit to the person who proved they were misbehaving.

The race condition that happens most frequently on the network today is the race condition in the ERC20 token standard. The ERC20 token standard includes a function called 'approve', which allows an address to approve another address to spend tokens on their behalf. Assume that Alice has approved Eve to spend n of her tokens, then Alice decides to change Eve's approval to m tokens. Alice submits a function call to approve with the value n for Eve. Eve runs an Ethereum node, so she knows that Alice is going to change her approval to m. Eve then submits a transferFrom request, sending n of Alice's tokens to herself, but gives it a much higher gas price than Alice's transaction. The transferFrom executes first so gives Eve n tokens and sets Eve's approval to zero. Then Alice's transaction executes and sets Eve's approval to m. Eve then sends those m tokens to herself as well. Thus, Eve gets n + m tokens, even though she should have gotten at most max(n,m).

## Remediation

A possible way to remedy race conditions in the submission of information in exchange for a reward is called a commit reveal hash scheme. Instead of submitting the answer, the party who has the answer submits hash(salt, address, answer) \[salt being some number of their choosing\]; the contract stores this hash and the sender's address. To claim the reward, the sender then submits a transaction with the salt, and answer. The contract hashes (salt, msg.sender, answer) and checks the hash produced against the stored hash. If the hash matches, the contract releases the reward.

The best fix for the ERC20 race condition is to add a field to the inputs of approve, which is the expected current value, and to have approve revert if Eve's current allowance is not what Alice indicated she was expecting. However, this means that your contract no longer conforms to the ERC20 standard. If it is important to your project to have the contract conform to ERC20, you can add a safe approve function. From the user's perspective, it is possible to mitigate the ERC20 race condition by setting approvals to zero before changing them.

## References

[General Article on Race Conditions](https://medium.com/coinmonks/solidity-transaction-ordering-attacks-1193a014884e)
[ERC20 Race Condition](https://docs.google.com/document/d/1YLPtQxZu1UAvO9cZ1O2RPXBbT0mooh4DYKjA_jp-RLM/edit#)

## Samples

### ERC20.sol

```solidity
pragma solidity ^0.4.24;

/** Taken from the OpenZeppelin github
 * @title SafeMath
 * @dev Math operations with safety checks that revert on error
 */
library SafeMath {

  /**
  * @dev Multiplies two numbers, reverts on overflow.
  */
  function mul(uint256 a, uint256 b) internal pure returns (uint256) {
    // Gas optimization: this is cheaper than requiring 'a' not being zero, but the
    // benefit is lost if 'b' is also tested.
    // See: https://github.com/OpenZeppelin/openzeppelin-solidity/pull/522
    if (a == 0) {
      return 0;
    }

    uint256 c = a * b;
    require(c / a == b);

    return c;
  }

  /**
  * @dev Integer division of two numbers truncating the quotient, reverts on division by zero.
  */
  function div(uint256 a, uint256 b) internal pure returns (uint256) {
    require(b > 0); // Solidity only automatically asserts when dividing by 0
    uint256 c = a / b;
    // assert(a == b * c + a % b); // There is no case in which this doesn't hold

    return c;
  }

  /**
  * @dev Subtracts two numbers, reverts on overflow (i.e. if subtrahend is greater than minuend).
  */
  function sub(uint256 a, uint256 b) internal pure returns (uint256) {
    require(b <= a);
    uint256 c = a - b;

    return c;
  }

  /**
  * @dev Adds two numbers, reverts on overflow.
  */
  function add(uint256 a, uint256 b) internal pure returns (uint256) {
    uint256 c = a + b;
    require(c >= a);

    return c;
  }

  /**
  * @dev Divides two numbers and returns the remainder (unsigned integer modulo),
  * reverts when dividing by zero.
  */
  function mod(uint256 a, uint256 b) internal pure returns (uint256) {
    require(b != 0);
    return a % b;
  }
}

contract ERC20 {

  event Transfer( address indexed from, address indexed to, uint256 value );
  event Approval( address indexed owner, address indexed spender, uint256 value);
  using SafeMath for *;

  mapping (address => uint256) private _balances;

  mapping (address => mapping (address => uint256)) private _allowed;

  uint256 private _totalSupply;

  constructor(uint totalSupply){
    _balances[msg.sender] = totalSupply;
  }

  function balanceOf(address owner) public view returns (uint256) {
    return _balances[owner];
  }

  function allowance(address owner, address spender) public view returns (uint256)
  {
    return _allowed[owner][spender];
  }

  function transfer(address to, uint256 value) public returns (bool) {
    require(value <= _balances[msg.sender]);
    require(to != address(0));

    _balances[msg.sender] = _balances[msg.sender].sub(value);
    _balances[to] = _balances[to].add(value);
    emit Transfer(msg.sender, to, value);
    return true;
  }

  function approve(address spender, uint256 value) public returns (bool) {
    require(spender != address(0));

    _allowed[msg.sender][spender] = value;
    emit Approval(msg.sender, spender, value);
    return true;
  }

  function transferFrom(address from, address to, uint256 value) public returns (bool) {
    require(value <= _balances[from]);
    require(value <= _allowed[from][msg.sender]);
    require(to != address(0));

    _balances[from] = _balances[from].sub(value);
    _balances[to] = _balances[to].add(value);
    _allowed[from][msg.sender] = _allowed[from][msg.sender].sub(value);
    emit Transfer(from, to, value);
    return true;
  }
}

```

### eth_tx_order_dependence_minimal.sol

```solidity
/*
 * @source: https://github.com/ConsenSys/evm-analyzer-benchmark-suite
 * @author: Suhabe Bugrara
 */

pragma solidity ^0.4.16;

contract EthTxOrderDependenceMinimal {
    address public owner;
    bool public claimed;
    uint public reward;

    function EthTxOrderDependenceMinimal() public {
        owner = msg.sender;
    }

    function setReward() public payable {
        require (!claimed);

        require(msg.sender == owner);
        owner.transfer(reward);
        reward = msg.value;
    }

    function claimReward(uint256 submission) {
        require (!claimed);
        require(submission < 10);

        msg.sender.transfer(reward);
        claimed = true;
    }
}

```

repository: SmartContractSecurity/SWC-registry

gha_license_id: MIT

repo_name: SmartContractSecurity/SWC-registry


text:
# PhotoAlbumManager API

Framework: Play 2.3

Build Tool: Gradle 3.4

JDK: 1.7

Gradle Tasks:

    Build
        -build or
        -playBinary

    Run
        -run or
        -runPlayBinary

Runs at **localhost:9000**

Routes can be found at **`conf/routes`**

Assumptions:

    1. I had confusion with Photo CRUD and adding/removing a photo to album. So currently, when delete is directly called
    on Photo, it doesn't update Albums' photo collection.
    2. There is no database. Used HashMap and initiated it on application start in `Global.java`
    3. Used default logger and it logs to `logs/applicaitons.log`
    4. Play currently doesn't ignore the ending '/' in request uri. There are workarounds but I hadn't implemented here.

Code Structure:

    app
        Controllers
        Global.java
    src
        dataMappers
        models
        services
    build.gradle

repository: saitejerupaka/PhotoAlbumManager

repo_name: saitejerupaka/PhotoAlbumManager


text:
# Magit – Matrix Github Bot.

A single binary that listens for [Github-Webhooks][git] and responds using the [Matrix] chat
network.

## Built with
### [Ruma] • [Matrix-sdk] • [Rocket]

[git]: https://docs.github.com/en/developers/webhooks-and-events
[Matrix]: https://matrix.org/
[Ruma]: https://www.ruma.io/
[Matrix-sdk]: https://github.com/matrix-org/matrix-rust-sdk
[Rocket]: https://github.com/SergioBenitex/Rocket

## Getting started

TODO

## License

[MIT](http://opensource.org/licenses/MIT)

gha_language: Rust


text:
# SimpleThumbnail

Simple and lightweight PHP Class to create thumbnails.

## Getting Started

Import the class

```php
include 'SimpleThumbnail.php';
```

Instance the class, configure size, load image source and set name of thumbnail

```php
$simpleThumbnail = new SimpleThumbnail;
$simpleThumbnail->setWidth(250);
$simpleThumbnail->setHeight(250);
$simpleThumbnail->setQuality(100);
$simpleThumbnail->generate("image.png", "thumb.jpg");
```

## Methods

There are some methods that you must use to generate your thumbnail:

* **setWidth(_int $width_)**

Set width of thumbnail, parameter must be a integer value.

* **setHeight(_int $height_)**

Set height of thumbnail, parameter must be a integer value.

* **setQuality(_int $quality_)**

Set quality of thumbnail, parameter must be a integer value between 1 and 100..

* **generate(_string $sourceImage, string $thumbnailTarget_)**

This method will load original image from a source path given as string on the first parameter and will generate a thumbnail with the size and quality given on settings methods.

The Thumbnail will be saved on the path passed as string on the second parameter.

## About

Its just a class who load original image and generate a thumbnail with a size and quality given.

#### Why?

This class is designed to be a simple and lightweight way to create thumbnails.

The idea came from my need to generate thumbnails and many classes that I found on the internet had several features that are not necessary to generate a simple thumbnail.

#### Who?
Created by [Guilherme Farias](http://guilhermefarias.com.br/), a web developer from Brazil.

#### License?
SimpleThumbnail is released under the terms of the [MIT license](https://github.com/guilhermefarias/SimpleThumbnail/blob/master/MIT-LICENSE).

repository: guilhermefarias/SimpleThumbnail

gha_language: PHP

repo_name: guilhermefarias/SimpleThumbnail


text:
# devops-mission-control #

One dashboard to rule them all.

![Screenshot of the Clusters page](doc/images/clusters-page.png)

* View all deployments in several k8s clusters on the one page
* Look for deployment across all k8s clusters
* View deployment details, like as status, IP, history of releases and list of pods

#### Quick start ####

```shell script
docker run -p 8080:8080 -v ~/.kube:/home/mission-control/.kube mission-control
```

The application will be accessible at http://localhost:8080.
In-docker execution uses example configuration from src/main/resources by default.
You can override embed configuration: `-v config:/etc/mission-control/override`.

#### Configuration ####

##### Clusters #####
There are two options how to configure clusters:

a) Importing clusters and security options from the configuration file for kubectl
(~/.kube/config). It's appropriate for the local or development environment.
```yaml
mission-control:
  clusters-source:
    type: kubeconfig
    kubeconfig:
      path: "~/.kube/config"
```

b) Defining clusters and tokens in the application's configuration file.
It's more appropriate to use in production.
```yaml
mission-control:
  clusters:
    - name: testing
      displayName: "TESTING A"
      host: "https://kubernetes.testing.example.com:6443"
      dc: "datacenter-name"
      tokenName: "test"
    - name: prod
      displayName: "PROD A"
      host: "https://kubernetes.production.example.com:6443"
      dc: "datacenter-name"
      tokenName: "prod"

  tokens:
    - name: test
      token: ""
    - name: prod
      token: ""
```

gha_language: Kotlin


text:
# Horizontal-ListView
A Simple libraby help you create a listview in horizontal. The Horizontal ListView can set to be an endless listview, for more detail please read the sample app.

# How To Use
Horizontal ListView now available in both maven and jcenter. In the Build.gradle add the following lines :

```groovy

buildscript {
    repositories {
        jcenter()
        //Uncommend bellow lines if you use maven
        /*
        maven {
        url 'https://dl.bintray.com/ducna01598/maven/'
      }*/
    }
    dependencies {
        classpath 'com.github.ducna01598:JHorizontalListView:1.0.1'
    }
}

```

gha_language: Java


text:
# LinqPadScripts
I use Linqpad for a lot of tests and decided to share some of those code snippets to everyone.

Please note that none of these are what I would consider ""Best Practices" for coding and are purely meant for proof of concepts and testing a very specific use case


text:
# AWS SMS Laravel notification

Send sms trough AWS SNS.

## Contents

- [Installation](#installation)
	- [Setting up the AWSSMS service](#setting-up-the-AWSSMS-service)
- [Usage](#usage)
	- [Available Message methods](#available-message-methods)
- [Changelog](#changelog)
- [Testing](#testing)
- [Security](#security)
- [Contributing](#contributing)
- [Credits](#credits)
- [License](#license)

## Installation

You can install the package via composer:

``` bash
composer require peec/aws-laravel-notification
```

You must install the service provider:

```php
// config/app.php
'providers' => [
    ...
    NotificationChannels\AWS\AWSSMSServiceProvider::class,
],
```

### Setting up the AWSSMS service

Add  to your `config/services.php`:

```php
// config/services.php
...
'awssms' => [
    'key' => env('AWSSMS_KEY'),
    'secret' => env('AWSSMS_SECRET'),
    'region' => env('AWSSMS_REGION'),
    'from' => env('AWSSMS_FROM'), // optional
    'max_price_usd' => '0.50' // Max price, sms wont send if price of the sms is more then this.
],
...
```

## Usage

Now you can use the channel in your `via()` method inside the notification:

``` php
use NotificationChannels\AWS\AWSSMSChannel;
use NotificationChannels\AWS\AWSSMSMessage;
use Illuminate\Notifications\Notification;

class AccountApproved extends Notification
{
    public function via($notifiable)
    {
        return [AWSSMSChannel::class];
    }

    public function toAwsSms($notifiable)
    {
        return (new AWSSMSMessage())
            ->content("Your {$notifiable->service} account was approved!");
    }
}
```

In order to let your Notification know which phone are you sending/calling to, the channel will look for the `phone_number` attribute of the Notifiable model. If you want to override this behaviour,
add the `routeNotificationForAws` method to your Notifiable model.

```php
public function routeNotificationForAws()
{
    return '+1234567890';
}
```

### Available methods

- `from('')`: Accepts a phone to use as the notification sender.
- `content('')`: Accepts a string value for the notification body.
- `type('Transactional')`: Either Transactional or Promotional. See aws docs for SNS SMS. The pricing of these vary.

## Changelog

Please see [CHANGELOG](CHANGELOG.md) for more information what has changed recently.

## Testing

``` bash
$ composer test
```

## Security

If you discover any security related issues, please email<EMAIL_ADDRESS>instead of using the issue tracker.

## Contributing

Please see [CONTRIBUTING](CONTRIBUTING.md) for details.

## Credits

- [Petter Kjelkenes](https://github.com/peec)
- [All Contributors](../../contributors)

## License

The MIT License (MIT). Please see [License File](LICENSE.md) for more information.

repository: peec/aws-laravel-notification

repo_name: peec/aws-laravel-notification


text:
# ndate

This is a CLI program that gives the current Nepali date (Bikram Sambhat date), converts Bikram Sambhat to AD date and vice versa.

## Description

ndate command can be used to retrieve current Nepali date.
Options available are -a and -b where -a converts Bikram Sambhat date to AD date and -b converts AD date to Bikram Sambhat date.

Below are some examples

- ndate

Above command gives the current Nepali date.
output = 2078-03-13

- ndate -b 1985-9-9

Above command converts 1985-9-9 (yyyy-m-d) to Bikram Sambhat date.
output = 2042-05-24

- ndate -a 2042-5-24

Above command converts 2042-5-25 (yyyy-m-d) to AD date.
output = 1985-09-09

Nepali Month can vary from 29 days to 32 days, and they are not fixed so there is not any fixed algorithm to crack the number of days in a nepali month for a particular year, therefore starting from 1970 BS to 2090 BS the number of months are hardcoded. Credit to https://github.com/medic/bikram-sambat for the hardcoded data range (1970 - 2090 BS).

### Note: The conversion only works from the Bikram Sambhat Range of 1970 BS to 2090 BS. If you have more data please feel free to contribute.

## Getting Started and Installing

User can download the source code and build it using cargo build and run it using cargo run command if rust is installed in the system, or user can directly download the binary provided which will be available soon for various devices and can directly execute the binary.

### Executing program

- Download the binary
- Install it in a folder where path is visible, for example /usr/local/bin in mac.
- Type ndate and it will give you the current nepali date, or use the options provided accordingly.

## Authors

Swoven Pokharel<EMAIL_ADDRESS>


text:
[Mathematical Model](https://github.com/valeriupredoi/COVID-19_LINEAR/blob/master/Mathematical_Model.md)

![Doubling Rate of Case Confirmations](kdAj6.png)
[Interactive Map](https://datawrapper.dwcdn.net/kdAj6/)

![Doubling Rate of Reported Deaths](WQXRP.png)
[Interactive Map](https://datawrapper.dwcdn.net/WQXRP/)

![Percentual infection of the population](foNWt.png)
[Interactive Map](https://datawrapper.dwcdn.net/foNWt/)

![Estimation of underreported infections](dUzze.png)
[Interactive Map](https://datawrapper.dwcdn.net/dUzze/)


text:
## Elasticsearch Geo Point clustering aggregation plugin

This plugin extends Elasticsearch with a `geo_point_clustering` aggregation, allowing to fetch [geo_point](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/geo-point.html) documents as clusters of points.
It is very similar to what is done with the official [geohash_grid aggregation](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/search-aggregations-bucket-geohashgrid-aggregation.html) except that final clusters are not bound to the geohash grid.

For example, at zoom level 1 with points across France, `geohash_grid` agg will output 3 clusters stuck to geohash cells u, e, s, while `geo_point_clustering` will merge these clusters into one.
This is done during the reduce phase.

Contrary to `geohash_grid` aggregation, buckets keys are a tuple(centroid, geohash cells) instead of geohash cells only, because one cluster can be linked to several geohash cells, due to the cluster merge process during the reduce phase.
Centroids are built during the shard collect phase.

Please note that [geo_shape data type](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/geo-shape.html) is not supported.

## Usage
### Install

Install plugin with:
`./bin/elasticsearch-plugin install https://github.com/opendatasoft/elasticsearch-aggregation-geoclustering/releases/download/v<IP_ADDRESS>/geopoint-clustering-aggregation-<IP_ADDRESS>.zip`

### Quickstart
#### Intro
```json
{
  "aggregations": {
    "<aggregation_name>": {
      "geo_point_clustering": {
        "field": "<field_name>",
        "zoom": "<zoom>"
      }
    }
  }
}
```
Input parameters :
- `field`: must be of type [geo_point](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/geo-point.html)
- `zoom`: mandatory integer parameter between 0 and 25. It represents the zoom level used in the request to aggregate geo points
- `radius`: radius in pixel. It is used during the reduce phase to merge close clusters. Default to `40`
- `ratio`: ratio used to make a second merging pass during the reduce phase. If the value is `0`, no second pass is made. Default to `0`
- `extent`: Extent of the tiles. Default to `256`

#### Real-life example

Create an index:
```json
PUT test
{
  "settings": {
    "number_of_shards": 1,
    "number_of_replicas": 0
  },
  "mappings": {
    "properties": {
      "location": {
        "type": "geo_point"
      }
    }
  }
}
```

Push some points:
```json
POST test/_bulk?refresh
{"index":{"_id":1}}
{"location":[2.454929, 48.821578]}
{"index":{"_id":2}}
{"location":[2.245858, 48.86914]}
{"index":{"_id":3}}
{"location":[2.240358, 48.863481]}
{"index":{"_id":4}}
{"location":[2.25292, 48.847176]}
{"index":{"_id":5}}
{"location":[2.279111, 48.872383]}
{"index":{"_id":6}}
{"location":[2.336267, 48.822021]}
{"index":{"_id":7}}
{"location":[2.338677, 48.822672]}
{"index":{"_id":8}}
{"location":[2.336643, 48.822493]}
{"index":{"_id":9}}
{"location":[2.438465, 48.84204]}
{"index":{"_id":10}}
{"location":[2.381554, 48.835382]}
{"index":{"_id":11}}
{"location":[2.407744, 48.83733]}
{"index":{"_id":12}}
{"location":[2.34521, 48.849358]}
{"index":{"_id":13}}
{"location":[2.252938, 48.846041]}
{"index":{"_id":14}}
{"location":[2.279715, 48.871775]}
{"index":{"_id":15}}
{"location":[2.380629, 48.879757]}
```

Perform an aggregation:
```json
POST test/_search?size=0
{
  "aggregations": {
    "clusters": {
      "geo_point_clustering": {
        "field": "location",
        "zoom": 9
      }}}}
```

Result:
```json
"aggregations" : {
    "clusters" : {
      "buckets" : [
        {
          "geohash_grids" : [
            "u09wn",
            "u09tz",
            "u09ty",
            "u09tx",
            "u09tv",
            "u09tt"
          ],
          "doc_count" : 9,
          "centroid" : {
            "lat" : 48.83695897646248,
            "lon" : 2.380013056099415
          }
        },
        {
          "geohash_grids" : [
            "u09w5",
            "u09tg",
            "u09tf"
          ],
          "doc_count" : 6,
          "centroid" : {
            "lat" : 48.86166598415002,
            "lon" : 2.258483301848173
          }
        }
      ]
    }
```

## Development environment setup
### Build

Built with Java 17 and Gradle 7.5.1 (use the packaged gradlew included in this repo if you want to build yourself).

### Development Environment Setup

Build the plugin using gradle:
``` shell
./gradlew build
```

or
``` shell
./gradlew assemble  # (to avoid the test suite)
```

Then the following command will start a dockerized ES and will install the previously built plugin:
``` shell
docker-compose up
```

Please be careful during development: you'll need to manually rebuild the .zip using `./gradlew build` on each code
change before running `docker-compose` up again.

> NOTE: In `docker-compose.yml` you can uncomment the debug env and attach a REMOTE JVM on `*:5005` to debug the plugin.


text:
---
layout: post
title:  "Pan fried meat with rich sauce"
date:   2018-12-07 19:10:00
publishdate:   2018-12-07 19:10:00
author: oli
tags: ["pan fried", "booze", "2018"]
image: "/images/blog/pan-chicken-booze-sauce/pan-chicken-booze-sauce-04.jpg"
---

There's nothing cleer here, in fact it's all a bit 70s French, but it is delicious.  If you want a cleaner finish, skip the onions.  For a richer one, finish with a drop of single cream.    For those who like mashed potato I'd guess this would go well  Add a leafy green veg (savoy cabbage this time of year) if you must be an adult.

Note: this is also a good way to ue up those ends of butter that you get whichhave gone a bit "fridgy" in smell

## You will need

* A chunk of meat.  See above.
* A couple of small onions.  I used pink ones because they were on offer and are sweet.
* About 100ml of booze. I used the ends of 2 vermouths and a sherry. Wine would also work.
* A tablespoon of flour
* Butter
* A handful of herbs.  I used parsley
* A couple of teaspoons of capers (mine were in brine from a jar)

## Do

* Slice the onions and pile into your pan with about 50g of butter
* Slice on a very low heat, cover and leave for 20 minutes stiring occationally or until the onions are soft and translucent, with a touch of colour
* Meanwhile, flour your chunk of meat and beat a bit flatter if needed.  I shook mine in a bag with a good pinch of salt and black pepper.
* Once the onions are done, scape the pan into a bowl and leave to one side
* Add another 50g or so of butter the pan and raise to a low heat
* Add the meat, there should be a slight sizzle
* Slick your plates on to warm.  Don't serve this on a cold plate
* Cook though, turning as needed.  This took a good 15 mins for the thick turkey breast.  I cut it in two at one point to make sure it was well cooked through.
* Set the meat to one side.  It should have a reasonable crusty sear
* If needed, add a bit more butter to the pan.  You want a good tablespoon of liquid sloshing round
* Add the herbs, capers, onions and booze, then turn up the heat and scape scape scape all the stuck on bits
* Serve once the sauce has reduced a little

## Result

Deeply savour sauce, thick and juice chunk of meat, look at the shimmer on that sauce.

![Before](/images/blog/pan-chicken-booze-sauce/pan-chicken-booze-sauce-01.jpg)
![First hitting the pan](/images/blog/pan-chicken-booze-sauce/pan-chicken-booze-sauce-02.jpg)
![After cooking](/images/blog/pan-chicken-booze-sauce/pan-chicken-booze-sauce-03.jpg)
![GET IN MY FACE](/images/blog/pan-chicken-booze-sauce/pan-chicken-booze-sauce-04.jpg)

repository: coldclimate/omnomfrickinnom

extension: markdown

gha_language: HTML

repo_name: coldclimate/omnomfrickinnom


text:
---
title: What's Difference Of Cny And Cnh
header:
    image: /assets/images/talk-about-CNY-vs-CNH.jpg
date: 2023-03-19
tags:
- JFR
- Java
- PerformanceTuning

permalink: /blogs/tech/en/talk-about-CNY-vs-CNH
layout: single
category: tech
---
# what's difference of CNY and CNH
CNY and CNH are both currencies used in China, but they are different in a few important ways:

CNY stands for "Chinese Yuan Renminbi" and is the official currency of China, while CNH stands for "Chinese Yuan Offshore" and is a version of the Chinese Yuan that is traded outside of China.

CNY is subject to strict government regulations and is only allowed to be traded within China's borders, while CNH is freely traded on foreign exchange markets.

CNH is typically used for international trade and investment transactions, while CNY is used for domestic transactions within China.

Because of the difference in trading restrictions and availability, CNH and CNY often have slightly different exchange rates. CNH is usually more expensive than CNY, reflecting the greater demand for it on the international market.

In summary, while both CNY and CNH represent the Chinese Yuan, they are used in different contexts and have different trading restrictions and exchange rates.

todd zhang
continue
Another significant difference between CNY and CNH is the way they are settled. Settlement refers to the process of exchanging one currency for another in a financial transaction. For CNY, settlement is done through the China National Advanced Payment System (CNAPS), which is a domestic payment system. On the other hand, CNH is settled through the Hong Kong Clearing House Automated Transfer System (CHATS), which is an offshore payment system.

The availability of CNY and CNH can also be affected by economic and political factors. For example, during periods of economic instability or political tension, it may be more difficult to trade or obtain one currency over the other.

Due to the different trading restrictions and settlement processes, CNY and CNH may have different liquidity levels. Liquidity refers to the ease with which a currency can be bought or sold in the market. In general, CNH tends to be more liquid than CNY due to its availability on the international market.

In summary, the differences between CNY and CNH are related to their availability, trading restrictions, settlement processes, exchange rates, and liquidity. While both currencies represent the Chinese Yuan, their distinct features make them suitable for different purposes and contexts.

todd zhang
give me a sample
Sure, here's an example of how CNY and CNH can be used in different contexts:

Let's say a Chinese company wants to import goods from the United States. The transaction will involve exchanging Chinese Yuan for US Dollars. The company can choose to pay for the transaction using either CNY or CNH, depending on their needs and preferences.

If the company has enough CNY in their domestic account, they can choose to settle the transaction using CNY. However, they will need to convert their CNY into US Dollars through a bank in China that is authorized to conduct foreign exchange transactions. This process may take longer and be subject to more regulatory restrictions.

Alternatively, the company can choose to settle the transaction using CNH, which can be freely traded on international markets. They can buy CNH with their CNY and then use the CNH to buy US Dollars. This process may be faster and more convenient, but the exchange rate for CNH may be different from the exchange rate for CNY, which means the company may need to pay a higher or lower amount depending on the exchange rate at the time of the transaction.

In summary, the choice between CNY and CNH depends on various factors such as availability, trading restrictions, settlement processes, exchange rates, and liquidity, and companies may choose to use one or the other based on their specific needs and circumstances.

gha_language: JavaScript


text:
# Jevo - Evolution simulations in Julia

[![Build Status](https://travis-ci.com/tomroesch/Jevo.jl.svg?branch=master)](https://travis-ci.com/tomroesch/Jevo.jl)
[![Build Status](https://travis-ci.org/tomroesch/Jevo.jl.svg?branch=master)](https://travis-ci.org/tomroesch/Jevo.jl)

## Why?
This package enables

## Setting up the environment

All code in this repository is written in Julia ([version 1.6](https://github.com/JuliaLang/julia/releases/tag/v1.6.0), can be installed from this link). Once Julia is installed, the standard Julia REPL can be started from the terminal, by navigating into the folder where Julia was installed, and running `path/julia/bin/julia`. On Mac, it should simply be `/Applications/Julia-1.x.app/Contents/Resources/julia/bin/julia` (we recommend setting an alias, x stands for the version of Julia that is installed).

To add this package, navigate into this folder and run:
```julia
julia> ] dev .
```

This adds the package in the development mode, and lets you add and change things at will. Make sure to include testing for additions to the package to ensure functionality. To test the package, the environment has to the activated. Therefore, run Julia with this directory as working directory and use:

```julia
julia> ] activate .

julia> ] test
```

## Basic Use
### Initializing a Population

Included in this package are a few number of population types of genetic possible genetic sequences composed of integers as letters. Population types are initialized as subtypes of the type `populations`.

```julia
julia> using Jevo
julia>? Jevo.populations
  No documentation found.

  Summary
  ≡≡≡≡≡≡≡≡≡

  abstract type Jevo.populations <: Any

  Subtypes
  ≡≡≡≡≡≡≡≡≡≡

  Jevo.DT_population
  Jevo.simple_sites
```

The most basic type is `simple_sites`, which consists of a population of single sequences with fixed length. To find information about the fields, simply check out the documentation.

```julia
julia>?Jevo.simple_sites
  mutable struct simple_sites <: populations

  Population of simple binding sites with fixed length.

  ...

  Arguments
  ≡≡≡≡≡≡≡≡≡≡≡

    •    N::Float64=1000: population size.

    •    l::Int64=10: Length of site.

    •    n::Int64=4: Alphabet size.

    •    seqs::Array{Array{Int64, 1}, 1}=[]: Array of sequences for each species.

    •    freqs::Array{Int64, 1}=[] Species sizes.

  ...

  Examples
  ≡≡≡≡≡≡≡≡≡≡

  julia> Jevo.simple_sites()
  Jevo.simple_sites(1000, 10, 4, Array{Int64,1}[], Int64[])
```

By default, populations are initiated without sequences, which are initiated in a later step. All parameters are given as keyword arguments. Initial sequences and frequencies can also be given if wanted.

```julia
julia> Jevo.simple_sites()
  Jevo.simple_sites(1000, 10, 4, Array{Int64,1}[], Int64[])

julia> Jevo.simple_sites(N=100, n=2, l=20)
Jevo.simple_sites(100, 20, 2, Array{Int64,1}[], Int64[])
```

If no initial sequences were given, they can be added by using the `initiate!` function, which takes a population and optionally the number of species as arguments (by default a single sequence is generated). Sequences are created randomly.

```julia
julia> pop = Jevo.simple_sites()
Jevo.simple_sites(1000, 10, 4, Array{Int64,1}[], Int64[])

julia> Jevo.initiate!(pop)

julia> pop
Jevo.simple_sites(1000, 10, 4, [[4, 2, 1, 4, 1, 1, 2, 2, 4, 2]], [1000])

julia> pop = Jevo.simple_sites()
Jevo.simple_sites(1000, 10, 4, Array{Int64,1}[], Int64[])

julia> Jevo.initiate!(pop, 5)

julia> pop.seqs
5-element Array{Array{Int64,1},1}:
 [2, 1, 4, 3, 2, 2, 3, 3, 2, 1]
 [2, 2, 3, 1, 4, 4, 2, 4, 4, 4]
 [3, 1, 2, 1, 1, 1, 2, 2, 4, 2]
 [2, 3, 2, 1, 4, 1, 3, 3, 4, 2]
 [2, 3, 3, 4, 1, 2, 2, 4, 4, 2]

julia> pop.freqs
5-element Array{Int64,1}:
 200
 200
 200
 200
 200
```

Other population types have more parameters, but are initialized in the same way. To see all population types that are included at the moment use the function `showtypetree`, which is copied from [wikibooks](https://en.wikibooks.org/wiki/Introducing_Julia/Types).

```
julia> showtypetree(Jevo.populations)
Jevo.populations
	Jevo.DT_population
		Jevo.driver_trailer
		Jevo.driver_trailer_l
		Jevo.mono_pop
	Jevo.simple_sites
```

Each of these types has its own `initiate!` function, but works the same for all types. What parameters are used for each type can be found in the documentation of each type. If a custom population is added to the package and used, make sure to define an appropriate `initiate!` function to the `initiate.jl` sub-module.

One can also generate a sequence which is optimally adapted, meaning it has minimal binding energy. Therefore, the second argument when initializing the sequence is an energy matrix.


text:
# GodotFireBase

GodotFireBase is a Firebase integration module for Godot Android.

### Project has been moved to newer repo [GDFirebase](https://github.com/FrogSquare/GDFirebase)

[![Platform](https://img.shields.io/badge/Platform-Android-green.svg)](https://github.com/FrogSquare/GodotFireBase)
[![GodotEngine](https://img.shields.io/badge/Godot_Engine-2.X%20/%203.X-blue.svg)](https://github.com/godotengine/godot)
[![LICENCE](https://img.shields.io/badge/License-Apache_V2-blue.svg)](https://www.apache.org/licenses/LICENSE-2.0)
[![PATREON](https://img.shields.io/badge/Patreon-support-yellow.svg)](https://www.patreon.com/bePatron?u=5130479)

# Depends on

> Godot game engine: `git clone https://github.com/godotengine/godot`

> GodotSQL: `git clone https://github.com/FrogSquare/GodotSQL`

# Available Features

> AdMob

> Analytics

> Authentication [W.I.P] Google, Facebook, Twitter

> Firebase Notification

> RemoteConfig

> Storage

> Firestore (W.I.P)

# Ready your project
* open `<GODOT>/platform/android/java/gradle.properties` and add the following line
```
android.useAndroidX=true
android.enableJetifier=true
```

# Build/Compile module

* Copy your `google-services.json` file to `[GODOT-ROOT]/platform/android/java/`
* Edit file modules/FireBase/config.py at line 11

```
p_app_id = "com.your.appid"     # config.py L:11
```

* Replace `com.your.appid` with you android application id.

* To build Admob you need to set your AdMob Application ID in the `AndroidManifestChunk.xml` file. To do this, edit the file `android_src/AndroidManifestChunk.xml`. Navigate to the end of the file. Replace the **value** for APPLICATION_ID with your real application ID.

*For customizing the module go [here](https://github.com/FrogSquare/GodotFireBase/wiki/Customize-GodotFireBase)*

# FAQ

**Should I rename the android_src folder after customization?**

> No, After customization the folder used by the module will be `android`, And `android_src` folder will be a backup for future customization.

# Initialize FireBase

Edit engine.cfg and add

```
[android]
modules="org/godotengine/godot/FireBase,org/godotengine/godot/SQLBridge"
```

RemoteConfigs default parameters `.xml` file is at `[GODOT-ROOT]/modules/FireBase/res/xml/remote_config_defaults.xml`

# GDScript - getting module singleton and initializing;

### On 2.X

```
var firebase = Globals.get_singleton("FireBase");
```

### On 3.X (latest from git)

```
var firebase = Engine.get_singleton("FireBase");
```

For Analytics only `firebase.init("", get_instance_ID())` or to user RemoteConfig or Notifications (subscribing to topic)

# GodotFireBase: copy `godot-firebase-config.json` to your projects root directord.
GodotFireBase config file, By default every feature is disabled.

```
{
	"AdMob" : true,
	"Authentication" : true,
	"RemoteConfig" : true,
	"Notification" : true,
	"Storage" : true,
	"Firestore" : true,

	"AuthConf" :
	{
		"Google" : true,
		"Twitter" : true,
		"Facebook" : true,
		"FacebookAppId" : "1234566789875"
	},

	"Ads" :
	{
		"AppId": "YOUR_APP_ID_HERE",
		"BannerAd" : true,
		"BannerGravity" : "BOTTOM",
		"BannerAdId" : "",

		"InterstitialAd" : true,
		"InterstitialAdId" : "",

		"RewardedVideoAd" : true,
		"RewardedVideoAdId" : "",

        "TestAds" : false
	}
}
```

And initialize firebase with file path, `RewardedVideoAdId` is a string array i.e `"string1,string2"`

```
func _ready():
    if OS.get_name() == "Android":
        firebase.initWithFile("res://godot-firebase-config.json", get_instance_ID())

func _receive_message(tag, from, key, data):
    if tag == "FrogSquare":
        print("From: ", from, " Key: ", key, " Data: ", data)
```

# Using FireBase Analytics

```
firebase.send_events("EventName", Dictionary)
firebase.send_custom("TestKey", "SomeValue")

firebase.setScreenName("Screen_name")
firebase.sendAchievement("someAchievementId")		# unlock achievement
firebase.join_group("clan_name")			# join clan/group
firebase.level_up("character_name", level)		# send character level
firebase.post_score("charcter name", level, score)	# post your score
firebase.earn_currency("currency", amount);		# when play earn some virtual currency gold/Diamond/any
firebase.spend_currency("item_id", "currency", amount)	# when user spend virtual currency

firebase.tutorial_begin()				# tutorial begin
firebase.tutorial_complete()				# tutorial end

Reference: https://support.google.com/firebase/answer/6317494?hl=en
```

# AlertDialog aditional

```
firebase.alert("Message goes here..!") # Show a simple AlertDialog
firebase.set_debug(true) # Enable/Disable `GodotFireBase` debug messages
```

# Authentication

For Facebook edit `res/values/ids.xml` and replace facebook_app_id with your Facebook App Id

```
firebase.authConfig("'Google':true,'Facebook':true") # Configure Auth service

firebase.get_id_token()

firebase.google_sign_in() # Firebase connect to google.
firebase.facebook_sign_in() # Firebase connect to facebook.
firebase.twitter_sign_in() # Firebase connect to twitter.
firebase.anonymous_sign_in() # Firebase connect anonymously.

firebase.google_sign_out() # Firebase disconnect from google.
firebase.facebook_sign_out() # Firebase disconnect from facebook.
firebase.twitter_sign_out() # Firebase disconnect from twitter.
firebase.anonymous_sign_out() # Firebase disconnect anonymously.

var gUserDetails = firebase.get_google_user() # returns name, email_id, photo_uri
var fbUserDetails = firebase.get_facebook_user() # returns name, email_id, photo_uri

firebase.google_revoke_access()
firebase.facebook_revoke_access()

firebase.is_google_connected() # bool check for google authentication (google)
firebase.is_facebook_connected() # bool check for facebook authentication (facebook)
firebase.is_anonymous_connected() # bool check for facebook authentication (anonymous)
```

More for facebook permissions

```
firebase.facebook_has_permission("publish_actions") # Check for availabe permission

firebase.revoke_facebook_permission("publish_actions") # revoke permission

firebase.ask_facebook_publish_permission("publish_actions"); # asking write permission

firebase.ask_facebook_read_permission("email"); # asking read only permission

firbase.get_facebook_permissions() # getting available permissions
```

Recive message from java

```
func _receive_message(tag, from, key, data):
    if tag == "FrogSquare":
        if from == "Auth":
            if key == "GoogleLogin" && data == "true": print("User Signed in.")
            if key == "FacebookLogin" && data == "true": print("User Signed in.")
```

# Firebase Notification API

```
firebase.subscribeToTopic("topic") # Subscribe to particular topic.
firebase.getToken() # Get current client TokenID

If recived notifiction has a payload, it will be saved inside SQL Database under key: "firebase_notification_data"

firebase.notifyInMins("message", 60) # Shedule notification in 60 min
firebase.notifyInSecs("message", 3200) # Shedule notification in 3200 seconds

var dict = {}
dict["title"] = "Notification title"
dict["message"] = "This is a text message"
dict["image_uri"] = "res://big_image_in_notification_body.png"
dict["type"] = "text"

firebase.notifyOnComplete(dict, 3200) # Shedule notification in 3200 seconds
```

# RemoteConfig API

```
firebase.getRemoteValue("remote_key") # Return String value
```

# Settings RemoteConfig default values

```
var defs = Dictionary()
defs["some_remoteconfig_key1"] = "remote_config_value1"
defs["some_remoteconfig_key2"] = "remote_config_value2"

firebase.setRemoteDefaults(defs.to_json())
```

OR load from json file

```
firebase.setRemoteDefaultsFile("res://path/to/jsonfile.json")
```

# Firebase Storage

```
# Upload Files from sdcard
firebase.upload("images/file", "destFolder") # uploads file from sdcard to firebase

# Download Files from Firebase
firebase.download("file", "images") # Saves file from firebase to sdcard
```

# Firebase AdMob

```
firebase.is_banner_loaded()     # Returns `true` if banner is loaded
firebase.is_interstitial_loaded() # Returns `true` if interstitial is loaded

firebase.show_banner_ad(true)	# Show Banner Ad
firebase.show_banner_ad(false)	# Hide Banner Ad
firebase.set_banner_unitid("unit_id") # Change current Ad unit ID

firebase.show_interstitial_ad() # Show Interstitial Ad
firebase.show_rewarded_video()	# Show Rewarded Video Ad
firebase.show_rvideo("unit_id") # Show Rewarded Video Ad

firebase.request_rewarded_video_status() # Request the rewarded video status
```

AdMob Recive message from java

```
func _receive_message(tag, from, key, data):
    if tag == "FrogSquare" and from == "AdMob":
        if key == "AdMobReward":
            # when rewared video play complete
            print("json data with [RewardType & RewardAmount]: ", data);

        elif key == "AdMob_Video":
            # when rewarded video loaded
            # data will be `loaded` or `load_failed and `loaded` or `not_loaded` with `firebase.request_rewarded_video_status()`
            print("AdMob rewarded video status is ", data);

        elif key == "AdMob_Banner":
            # when banner loaded
            # data will be `loaded` or `load_failed`
            print("Banner Status: ", data);

        elif key == "AdMob_Interstitial" and data == "loaded":
            # when Interstitial loaded
            # data will be `loaded` or `load_failed`
            print("Interstitial Status: ", data);
```

# Firebase Firestore

```
firebase.add_document("collection_name", dict) # Auto created new Document under collection_name
firebase.set_document("collection_name", "document_name", data) # Set document data, Data's are merged by default
firebase.load_document("collection_name") # load or retrive from the server,

# Note: documents will be sent to the `_receive_message` function as json
```

# Sharing
```
# Simple text based sharing. Include links if needed. 'Subject' can be null or empty.
firebase.share("Message", "Subject")
```

# Note

While exporting, don't forget to add `*.json` under Resources tab,
![alt text](http://preview.ibb.co/fTwC8Q/Screenshot_from_2017_06_17_18_44_25.png)

# Log Event

```
adb -d logcat godot:V FrogSquare:V DEBUG:V AndroidRuntime:V ValidateServiceOp:V *:S
```

repository: FrogSquare/GodotFireBase

repo_name: FrogSquare/GodotFireBase


text:
# vxlan create

### Description

The `create` sub-command under the `tools vxlan` command creates a VxLAN interface and sets `tc` rules to redirect traffic to/from a specified interface available in root namespace of a container host.

This combination of a VxLAN interface and `tc` rules make possible to transparently connect lab nodes running on different VMs/hosts.

VxLAN interface name will be a catenation of a prefix `vx-` and the interface name that is used to redirect traffic. If the existing interface is named `srl_e1-1`, then VxLAN interface created for this interface will be named `vx-srl_e1-1`.

### Usage

`containerlab tools vxlan create [local-flags]`

### Flags

#### remote
VxLAN tunnels set up with this command are unidirectional in nature. To set the remote endpoint address the `--remote` flag should be used.

#### id
VNI that the VxLAN tunnel will use is set with `--id | -i` flag. Defaults to `10`.

#### link
As mentioned above, the tunnels are set up with a goal to transparently connect containers deployed on different hosts.

To indicate which interface will be "piped" to a VxLAN tunnel the `--link | -l` flag should be used.

#### dev
With `--dev` flag users can set the linux device that should be used in setting up the tunnel.

Normally this flag can be omitted, since containerlab will take the device name which is used to reach the remote address as seen by the kernel routing table.

#### mtu
With `--mtu | -m` flag it is possible to set VxLAN MTU. Max MTU is automatically set, so this flag is only needed when MTU lower than max is needed to be provisioned.

### Examples

```bash
# create vxlan tunnel and redirect traffic to/from existing interface srl_e1-1 to it
# this effectively means anything that appears on srl_e1-1 interface will be piped to vxlan interface
# and vice versa.

# srl_e1-1 interface exists in root namespace
❯ ip l show srl_e1-1
617: srl_e1-1@if618: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP mode DEFAULT group default
    link/ether fa:4c:16:11:11:05 brd ff:ff:ff:ff:ff:ff link-netns clab-vx-srl1

# create a vxlan tunnel to a remote vtep <IP_ADDRESS> with VNI 10 and redirect traffic to srl_e1-1 interface
❯ clab tools vxlan create --remote <IP_ADDRESS> -l srl_e1-1 --id 10
INFO[0000] Adding VxLAN link vx-srl_e1-1 under ens3 to remote address <IP_ADDRESS> with VNI 10
INFO[0000] configuring ingress mirroring with tc in the direction of vx-srl_e1-1 -> srl_e1-1
INFO[0000] configuring ingress mirroring with tc in the direction of srl_e1-1 -> vx-srl_e1-1

# check the created interface
❯ ip l show vx-srl_e1-1
619: vx-srl_e1-1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1400 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000
    link/ether 7a:6e:ba:82:a4:6f brd ff:ff:ff:ff:ff:ff
```

repository: burnyd/containerlab

repo_name: burnyd/containerlab


text:
---
title: MindQuest
subtitle: Climate & Global Warming - a geologist’s viewpoint
layout: page
date:   2020-10-08 18:30:00
categories: Al
tags: [MindQuest]
bigimg: /img/mindquest.jpg
---

EVERYONE talks about the weather! So why not MindQuest?

> Do we or don’t we... have climate warming - and if so, is fossil fuel causing it?

We are all familiar with the signs of a warming planet: Violent weather, wildfires, melting glaciers/ice sheets and, of course, days that seem warmer than ever before. This leads us to assume three things:

* unusual weather events are the result of a warming climate
* warming climate is caused by the rise in atmospheric CO2 levels
* the rise in atmospheric CO2 levels is caused by the use of oil and gas

So, the natural questions are: What should/can we do about it? Will we reach a tipping point?

In Thursday night’s presentation, we focus on these assumptions and questions. Colorado-based (Anthem snowbird) geologist Allen (Al) Heinrich will:

1. walk us through the above points,
2. explain how we can make sense of “climate data/observations/predictions,” and
3. what the future climate may look like, all from a geological perspective.

Mind you, geology is not just about rocks; it is deep time history about how the Earth’s chemical/physical systems have operated and interacted throughout time—and still do. And as such, it provides an insight into how they may behave in the future.

A lot of this information will be new to most observers, so don’t miss this event.

Whichever way it goes, you’ll have to live with the weather . . . and you want to have something to keep talking about.

We hope to see you there.

### Follow-Up

* [Zoom Recording](https://drive.google.com/file/d/1hxWEijlx3ux21cV_-d1roMRIqOZbCfxe/view?usp=sharing) (Video)

gha_license_id: NOASSERTION


text:
[![CI Status](https://img.shields.io/travis/Abedalkareem/AMDots.svg?style=flat)](https://travis-ci.org/Abedalkareem/AMDots)
[![Version](https://img.shields.io/cocoapods/v/AMDots.svg?style=flat)](https://cocoapods.org/pods/AMDots)
[![License](https://img.shields.io/cocoapods/l/AMDots.svg?style=flat)](https://cocoapods.org/pods/AMDots)
[![Platform](https://img.shields.io/cocoapods/p/AMDots.svg?style=flat)](https://cocoapods.org/pods/AMDots)

AMDots is a loading indicator with dots moving like google loading, there are three types of the loading, scale, jump, and shake.

## Screenshots

## Example

### Code example

```swift
class CodeExampleViewController: UIViewController {

  private var dotsView: AMDotsView!

  override func viewDidLoad() {
    super.viewDidLoad()

    dotsView = AMDotsView(frame: CGRect(x: 20, y: 20, width: 150, height: 70),
                          colors: [.red, .blue, .yellow, .green])
    dotsView.backgroundColor = UIColor.white
    dotsView.animationType = .scale
    view.addSubview(dotsView)

    dotsView.start()
  }
}
```

### Storyboard example

```swift
class StoryboardExampleViewController: UIViewController {

  @IBOutlet weak var dotsView1: AMDotsView!

  override func viewDidLoad() {
    super.viewDidLoad()

    dotsView1.animationType = .jump
    dotsView1.aheadTime = 0.5
    dotsView1.animationDuration = 0.7
    dotsView1.start()
  }

}
```

## Installation

AMDots is available through [CocoaPods](https://cocoapods.org). To install
it, simply add the following line to your Podfile:

```ruby
pod 'AMDots'
```

## Author

Abedalkareem<EMAIL_ADDRESS>
## License

AMDots is available under the MIT license. See the LICENSE file for more info.

repository: Abedalkareem/AMDots

gha_language: Swift

repo_name: Abedalkareem/AMDots


text:
# BeWhy Genesis

### Hi,

"Jumping" cordialities, this git should **not** be *public*, but two decades of personal experience are culminating in this project experiment. Has a developer/analyst, which had the honor to initialize server**s**, and project's mentor, wanted to add that the main goal
is to design a code architecture, which will enable:
- Avoiding repetition of ANY  standard code in new client projects, eg. login;
  - this login also reflects roles and permissions, and it's own management, all in due time;
- Any new client project is an opportunity or to review code, add missing function, or even create a new inner-stack;
  - new clients bring more code to Genesis, and this architecture will spread to all running Genesis clients, eg. one billing becomes all billing;
- Present day DevOps allows multi-layers of code access and responsibilities:
  - while seniors are back-back-office (Genesis), juniors can focus on client code-folders, we can position specialists on it's folder/stack.

We don't want to bring one more PHP-framework to the ecosystem, nor market Genesis has as it's own "trademark", but it is our professional tool-box that implement businesses at BeWhy!

It was stated that **shouldn't** be public, since is real code in real servers... That is one mind-set! Is it ours???
We only got here with a lot of help from the *open-source* community, and as we will see later, we still use other people's code as dependencies...

BeWhy, more then a company is an ideology, and Genesis is a commitment to a chosen path...

### Getting Started
It wasn't stated before, but Genesis is not a full-on WebFramework, we are not re-inventing the wheel in every front! We are just following several best practices in one full-stack "development-result" structure.

At this point, you should understand that complete tutorial is at our homepage: [BeWhy Genesis](https://bewhy.org/genesis), but we only provide support to our corporate clients.

Genesis, itself does not work, so no use for you to clone or download **git**. Genesis will only interact with our chosen MVC, [Laravel 6.x](https://laravel.com).

### Prerequisites
As previous stated, Genesis is a tool-box with many components, which jump-start any project from 0 to deploy in *no-time*.

*Check complete tutorial page: [BeWhy Genesis](https://bewhy.org/genesis) or under [Built With](#built-with) and [Versioning](#versioning) chapters.*

The only prerequisite is [Laravel 6.x](https://laravel.com), your chosen dev environment and brain, the ladder is important...

Case you didn't drink enough coffee yet, **installing Laravel Environment is a must!**
- First: [Homestead](https://laravel.com/docs/6.x/homestead)
- Then: [Laravel Install](https://laravel.com/docs/6.x/installation)

Before continuing our tutorial, check your local site is okey!

It's mandatory, at this point, you gave some experience under Laravel, and know the tricks around files like:
```
    Homestead.yaml && \etc\hosts && .env
```
And you have your local server and composer updated...
Ready, set, go???

### Built With
Before install, a reminder that you should always look at [BeWhy Genesis](https://bewhy.org/genesis) for latest update.

We need to reference the following amazing teams, for their code, inspiration and contribution to world's coding community. We hope we will be worthy on following your legacy and improve on it.
For now all glory should go to:
* [codecalm/tabler](https://github.com/tabler/tabler) - Bootstrap4 Template we build upon.
* [arcanedev/localization](https://github.com/ARCANEDEV/Localization) - Easy i18n localization for Laravel, an useful tool to combine with Laravel localization classes.
* [laravelcollective/html](https://laravelcollective.com/docs/6.0/html) - Official documentation for Forms & Html for The Laravel Framework.
* [spatie/laravel-activitylog](https://docs.spatie.be/laravel-activitylog/v3/introduction/) - Easy to use functions to log the activities of the users of your app.
* [spatie/laravel-permission](https://docs.spatie.be/laravel-permission/v3/introduction/) - Manage user permissions and roles in a database.
* [barryvdh/laravel-debugbar](https://github.com/barryvdh/laravel-debugbar) - Adds a cool bar to footer in dev environment with displays of Redirects and (jQuery) Ajax Requests and Queries and more.
* [barryvdh/laravel-ide-helper](https://github.com/barryvdh/laravel-ide-helper) - This package generates a file that your IDE understands, so it can provide accurate auto-completion.
* [intervention/image](http://image.intervention.io/) - Intervention Image is an open source PHP image handling and manipulation library.

Under [Versioning](#versioning) chapter we will add some mode details to our actual code, but this thread is a special reference to those who deserve it.
Next topic we will see how to install all this in a couple of simple step's, and we will dive into examples how to interact will Genesis.

### Installing
Just start, a new Laravel Project... One way would be:
```
    composer create-project laravel/genesis client
```
You should have a minimum Laravel running at http://client.xyz

Run something like (depending on your SO, and prior configs)
```
    vagrant ssh    #connect to your server
    cd client      #go to you new project
    composer require bewhy/genesis --dev
    composer update
```
A huge log will ensure, it is importing Genesis, our code plus our requirements.... The *open-source* motive again! Just let it finish, hopefully everything ends in success, and we keep our bond of trust!

Before moving to next chapter, you will need to run
```
    php artisan vendor:publish --provider="BeWhy\Genesis\GenesisServiceProvider" --tag="assets"
```
This will enable template to be copy to: *public/template/genesis/docs/index.html*, so if you have no styles, this might be missing!
You can go check it out starting point... We added out add-ons on *public/css/genesis.css*, and don't forget to extend [BootStrap 4.0](https://getbootstrap.com/docs/4.0/layout/overview/) rules....

### Finishing

Our job is still not done, we just added some other dependencies that have to be implemented before system is fully running.

So at this point, just head to you dev site, and look up how to end the installation, should be something like http://client.xyz/genesis. Don't worry those route groups are only available on local environment (reference to .env).

## Deployment

This is the fun fact about BeWhy and/or Genesis, our clients have their own GitLab, and Genesis is on GitHub. Our projects have their Genesis + own dependencies, and Genesis is already a package of dependencies and exclusive business logic. That is why you have 2 step deployment, but you'll keep getting goodies everytime

````
composer update
````

This is one of the ways we ensure a solid and separate growth of software, having a main branch over time, and you can keep you independence. It seems I'm doing double the work, but after working with many stacks, teams, changing devs, and other "client" histories...

 Don't complain, do better... This is Genesis.

## Contributing

Even though we are showing raw code, contributions are by invitation only. If you're interested in working for us, you might send your job application to<EMAIL_ADDRESS>
For people who where added as **Git Users** of Genesis, I also leave a tip how to best separate our source from whatever everyone is doing.

Doing in fast forward mode:
```
    composer create-project laravel/genesis genesis
    vagrant ssh
    cd genesis
    mkdir packages/BeWhy/Genesis
    cd packages/BeWhy/Genesis
    git pull https://github.com/bewhy-pt/genesis.git
    composer dump-autoload
    cd ~/genesis | cd -
    vi composer.jon           #look and replace
        "autoload": {
            "psr-4": {
                "BeWhy\\Genesis\\": "packages/BeWhy/Genesis/src",
                "App\\": "app/"
            },
            "classmap": [
                "database/seeds",
                "database/factories"
            ]
        },
        "autoload-dev": {
            "psr-4": {
                "BeWhy\\Genesis\\": "packages/BeWhy/Genesis/src",
                "Tests\\": "tests/"
            }
        },
    composer update
    php artisan vendor:publish --provider="BeWhy\Genesis\GenesisServiceProvider" --tag="assets"
```
And you should have everything up and running! Has any dev, you will use Laravel directory structure to check the "bounds" of your Genesis code, which is everything in folder *packages/BeWhy/Genesis*.

In theory, and please **DON'T**, every client can have it's git to Genesis, and other git to client due tue directories structure. (if you use this, don't forget to add folder to .gitignore of client).

It's preferable to use *packages/BeWhy/Genesis* has IDE root too; and since you genesis.xyz calls "bounds" of Laravel and unknown (aka Genesis), you will have a better perception between the 3 worlds: Laravel, Genesis, Client.

## Versioning

Once again, a reminder that you should always look at [BeWhy Genesis](https://bewhy.org/genesis) for latest update. For the source versions available, see the [check GitHub](https://github.com/bewhy-pt/genesis).

Assuming this file will be forgotten, let's project the future for our version; and yes, a better versioning solution.

- [ Phase 0 ] - Setting up BeWhy & Genesis global
- [ Phase 1 ] - Import first bundle
    - template - which will run Genesis template for tutorial, or extented to site layout;
    - Settings - Helps with management of global vars and other dependencies (eg. roles permissions);
    - Crm - *Client Relationship Manager* - manages profiles, avatars, status, history;
    - Igm - *In Genesis Message* - messaging system between users;
    - Shop - *Phase 0* - Adding file struture, but first break-point;
    - File - To upload an attach files to all the above;

- [ Future Phases ] - More bundles to add
    - SOLID integration on Genesis Phase 1
    - Auth by Passport, not by regular Laravel\Auth (more private)
    - PaymentSystems - PayPal, Stripe
    - Versioning

## License

This project is licensed under the MIT License - see the [LICENSE.md](LICENSE.md) file for details

## Acknowledgments

* First: God, for creating everything
* Second: devil, for developing Math

repository: bewhy-pt/genesis

repo_name: bewhy-pt/genesis


text:
---
layout: post
title: "Let's Crunch Intelligence Squared"
description: ""
category:
tags: [random]
---

**Intelligence Squared US** is a cool debate series I listen to on NPR every so often. Debate topics include "Death Is Not Final" and "Russia Is A Marginal Power." Debates feature two sides: one for the motion and one against the motion.

The audience is polled on their opinion before and after the debate; they can vote for the motion, against the motion, or be undecided. The winner of the debate is whichever side has the largest increase in percentage points. So if the split is 70/20/10 (for / against / undecided) before the debate and 72/25/3 after the debate, the against side wins because they increased by 5 points, whereas the for side only gained 2 points. Winning usually boils down to whoever can sway the most undecided voters.

The other day a friend observed that, "I've listened to dozens of episodes, and not once has the number of unsure audience members increased." While it seems intuitive to me that fewer people would be undecided after hearing an extended discussion on a topic, I can also see where his confusion comes from. If you hear people present compelling arguments for two sides of a topic, it should have the power to convince some that their former positions may be incorrect -- maybe even sway some to decide that they are now undecided. I suppose people dislike NOT having an opinion.

A friend of disappointed friend, who also happens to be a data scientist, then crunched some numbers and wrote a [spectacular write-up][1] with some pretty interesting finds.

Said data scientist inputted all data into Google Spreadsheets before crunching some conclusions out, but **I'm a JSON-type-of-guy**. Enter [intelligence-json][2]: a repository containing all results of Intelligence Squared US debates in JSON format. Also enter [intelligence-analyzer][3]: a skeleton project that parses all this data into POJOs using Jackson, my favorite JSON parsing library.

Crunch away friends!

[1]: http://havingneweyes.com/2014/07/27/intelligence-squared-debates-voting-data/
[2]: https://github.com/markcerqueira/intelligence-json
[3]: https://github.com/markcerqueira/intelligence-analyzer


text:
---
title: "A Statistical Analysis of All Hacker News Submissions"
date: 2014-02-24T08:00:00-07:00
slug: hacking-hacker-news
categories: [Data Science]
tags: [R, ggplot2, Hacker News]
summary: "After downloading all 1,265,114 Hacker News submissions from the official Hacker News API, I gathered a few interesting statistics which show the true impact of Hacker News."
cover:
  image: featured.png
  relative: true
  hidden: true
---

[Hacker News](https://news.ycombinator.com/news) is a very popular link aggregator for the technology and startup community. Officially titled [by Paul Graham in 2007](http://ycombinator.com/hackernews.html), Hacker News began mostly as a place where the very computational-savvy could submit stories around the internet and discuss the latest computing trends.

{{< figure src="hn-wordcloud-2007i.png" theme="light" >}}

Back then, people were talking about networking, software users, and a little up-and-coming startup known as "[Twitter](https://twitter.com/)."

Six years later, during the new renaissance of computing accessibility and startup entrepreneurship, not much has changed.

{{< figure src="hn-wordcloud-2013i.png" theme="light" >}}

Hacker News, from 2007 to 2014, always illustrates what's "new" in technology. After downloading all 1,265,114 Hacker News submissions from the official [Hacker News API](https://hn.algolia.com/api), I gathered a few interesting statistics which show the true impact of Hacker News.

## How many stories are submitted to Hacker News?

In the past few years, Hacker News has had an interesting growth pattern.

{{< figure src="hn-monthly-submissions.png" theme="light" >}}

From the beginning of 2010 with 12k monthly submissions to to the end of 2011 with 31k monthly submissions, the amount of monthly submissions to Hacker News nearly tripled. It's a similar growth rate to that of the startups that Y Combinator typically funds.

What's _really_ interesting is that the end of 2011 is the peak: since then, the amount of submissions has been trending downward. Is Hacker News dying?

I don't think so. Hacker News implements a proprietary anti-spam algorithm which "kills" submissions, and moderators can kill submissions manually if necessary. Killed articles do not appear in the submission count, so a change in policy would cause the discrepancy. At the least, it helps improve the quality of discussion.

_UPDATE (2/28): Paul Graham, in the [corresponding HN thread](https://news.ycombinator.com/item?id=7291531), made a [comment](https://news.ycombinator.com/item?id=7292094) that the anti-spam algorithm did indeed increase spam detection and number of article killed at the end of 2011._

## How many submissions receive large amounts of points?

On Hacker News, users are able to upvote submissions. The more upvotes a submission has, the higher the position that it appears on the front page of the main site. A simple heuristic for calculating exposure from a Hacker News front page submission is 100 page views per point minimum, which means a submission that earns hundreds of points can go viral very quickly!

{{< figure src="hntop.png" theme="light" >}}

But how many submissions actually make it to the front page, and how many actually make it to the top?

{{< figure src="hn-points-hist.png" theme="light" >}}

On a logarithmic scale, it's evident that the vast majority of Hacker News submissions don't even hit 10 points. (the average amount of points for a submission is 9.51). Usually, hitting 10 points is the sign that you've appeared on the front page atleast briefly; there, the submission either receives voting momentum or dies quickly due to other rising stars.

But how many submissions _do_ receive hundreds of points? Here's a chart of submissions by month which have received more than 100 points:

{{< figure src="hn-monthly-submissions-front.png" theme="light" >}}

The growth rate of top-scoring submissions is correlated with the growth rate of Hacker News submissions themselves, which is not surprising. The number of points a post receives is also dependent on the number of users; as Hacker News grows, the number of users grows as well. Even though the front page cycles frequently, there is still room for great content.

## When is the best time to submit to Hacker News?

The age old question. What is the best time to post such that your post makes it to the front page?

First, let's see when Hacker News has the most activity by observing the average number of submissions for each combination of submission hour and weekday:

{{< figure src="hn-submissions.png" theme="light" >}}

Hacker News activity is most active at around 12 PM EST / 9 AM PST at about 40 submissions per hour, when hackers on the East Coast submit just before eating lunch, and hackers on the West Coast submit just after getting to work. Weekends, unsurprisingly, are completely dead.

If you submitted your link at 12 PM, you'd have a lot competition, but it would be easier to get upvotes since there would be more people visiting the site. If you submitted your post on the weekend, there would be no competition, but would be harder to make the front page.

What is the best weekday + hour to submit such that your submission goes viral? An easy way to estimate the best time is to analyze the times of submission of previous posts with large amounts of points; with enough data (we have enough), it'll provide a strong guess.

{{< figure src="hn-front-page.png" theme="light" >}}

As it turns out, the submission times of posts are _uncorrelated_ with the number of viral posts. There are _slightly_ more when submitting at peak activity (weekdays at 12 PM EST / 9 AM PST), but it won't make-or-break an article's success on HN.

Having good content is more important to having a post get to the top of Hacker News. Although you probably shouldn't submit an article when there's a major tech event. (e.g. Facebook's WhatsApp Purchase)

_UPDATE (2/28): It's been pointed out that measuring the proportion of viral posts (number of viral submissions / number of total submissions) would be a better indicator of odds of article success. Since the number of viral submissions is similar across all time zones, the proportion of viral posts would be greatest on the weekends, since there are dramatically fewer total submissions. However, this logic isn't perfectly correct due to how the article discovery and upvoting system works. I may cover this in a future post._

## Do Y Combinator startup announcements score better on HN?

One of the main benefits of Hacker News is to showcase the startups which Y Combinator has funded. Links about YC Startups contain the YC class name of that startup in their title, such as "[Watsi (YC W13) raises $1.2M first-of-its-kind philanthropic seed round](https://news.ycombinator.com/item?id=6103506)." Do these links perform better than the typical links submitted to Hacker News?

{{< figure src="hn-points-class-hist.png" theme="light" >}}

As it turns out, yes. For normal posts, the average number of points is 9.5 points, but for YC class announcements, the average is 41.7 points (from 1,745 submissions analyzed).

For fun, which YC classes perform the best on Hacker News?

{{< figure src="hn-top-class.png" theme="light" >}}

W06 placed first because of [two](https://news.ycombinator.com/item?id=2481576) [announcements](https://news.ycombinator.com/item?id=2481610) about Wufoo, and S11 placed second because of [CryptoSeal](https://news.ycombinator.com/item?id=6585071) and [Parse](https://news.ycombinator.com/item?id=2846725).

## Who are the best submitters on Hacker News?

Like all popular link aggregators, Hacker News has many spammers who submit large amounts of low quality content. Who are the users who submit quality content?

Calculating the average points of a user's submitted content isn't an accurate measurement, since that can be heavily skewed by one viral post. Therefore, I created a Hacker News "[batting average](http://en.wikipedia.org/wiki/Batting_average)" statistic: which posters have the highest proportion of posts that make it to the front page vs. the total number submitted? (for posts since 2010 and number of submitted posts >= 10)

{{< figure src="hn-top-submitters.png" theme="light" >}}

It should be no surprise that most of the people on the list are startup founders. It's also not surprising that most of those founders, such as [mwseibel](https://news.ycombinator.com/user?id=mwseibel), [rahulvohra](https://news.ycombinator.com/user?id=rahulvohra) and [tikhon](https://news.ycombinator.com/user?id=tikhon) also founded a Y Combinator startup. (although Paul Graham [himself](https://news.ycombinator.com/user?id=pg) only has a 0.856 average).

## What are Hacker News' favorite programming languages?

One of the infamous memes about Hacker News is programming language elitism, with favoritism for languages such as Lisp and Erlang.

But what programming languages are indeed the most popular on Hacker News?

{{< figure src="hn-lang-num-submissions.png" theme="light" >}}

Javascript is very popular, especially with the rising popularity of node.js. Go is unexpectedly frequently submitted for being such a new language. (although it's possible for "go" to be used in a context outside of a programing language.) Lisp and Erlang are indeed obscure, which might discredit the meme.

Which programming languages are most well-liked on HN?

{{< figure src="hn-lang-avg-submissions.png" theme="light" >}}

...so Lisp and Erlang _are_ well-liked on HN.

At the least, in both cases, no one on Hacker News likes PHP.

## Snowden and Bitcoin

Edward Snowden's leaks in June 2013 about the NSA and PRISM affected the entire tech industry, including Hacker News. How did Hacker News react to the leaks?

{{< figure src="hn-snowden.png" theme="light" >}}

Strongly.

But after the June spike, discussion about the NSA decreased significantly, but it's still a popular topic.

Bitcoin is more interesting since it has had three distinct surges:

{{< figure src="hn-bitcoin.png" theme="light" >}}

The June 2011 spike was due to the theft of [25,000 Bitcoin](https://bitcointalk.org/index.php?topic=16457.0), the April 2013 spike happened during the first rise-and-fall from $200/BTC, and the November 2013 spike happened during the second rise-and-fall from $1,000/BTC.

Hacker News is a great model for a link aggregator. It emphasizes more on quality content than the quantity of content, and it has paid off over the years.

---

_Code for getting all the HN submissions is [available on GitHub](https://github.com/minimaxir/hacker-news-download-all-stories). Unfortunately, the Hacker News data is too large to distribute freely. [Contact me](http://minimaxir.com/contact/) if you want the raw data or any data to reproduce the charts._

_Note: there appear to be [some gaps in the data](https://docs.google.com/spreadsheets/d/1Zdex42KE-8DFIHujhVWjJ3yqilJSws2EbT8VAARPYgE/edit?usp=sharing) for dates before 2010. This appears to be caused by the API server: for example, compare the [number of submissions as reported by HN for top user liebke](https://news.ycombinator.com/submitted?id=liebke) (21) and the [number of submissions as reported by the API](https://hn.algolia.com/api/v1/search_by_date?tags=story,author_liebke) for liebke (14, with the last 7 submitted stories missing relative to the HN output). Also, number of stories (1,265,114) in the output data and the [server data](https://hn.algolia.com/) (~1,267,000 as of publishing) are very close, making the discrepancy unlikely caused by client error. As a result, any chart that is based on a time series does not start earlier than 2010._


text:
## ECS Microservices application on AutoScaling Group & Capacity Providers

For the NEW Microservices application, we will henceforth call this NEW_Microservices.

In this sample, we will implement some of the strategies discussed here into a Microservices Nodejs sample application. Lets call it Old (pre-applying some of these strategies) and New(after implementing strategies).

Reference link :

In this example the microservices application is deployed on ECS.

![Reference architecture of microservices on EC2 Container Service](../images/new-microservice-containers-ecs.png)

## Changes made to the architecture

The sample has 3 services defined behind an Amazon Application Load Balancer (ALB), and we create rules on the ALB that direct requests that match a specific path to a specific service.
So each service will only serve one particular class of REST object, and nothing else. This will give us some significant advantages in our ability to independently monitor and independently scale each service.

__Cluster AutoScaling and Capacity Providers__

ECS Cluster Auto Scaling is a new capability for ECS to manage the scaling of EC2 Auto Scaling Groups. With Cluster Auto Scaling, you can configure ECS to scale your ASG automatically, and just focus on running your tasks. ECS will ensure the ASG scales in and out as needed with no further intervention required. To fill the gap of Managed Autoscaling, where ECS and EC2 instances can communicate scaling effectively, we launched a new feature in ECS called as ECS Capacity Providers. Cluster Auto Scaling relies on ECS capacity providers.

__Use combination of OnDemand with Spot instances__

Spot Instances have same as pay-as-you-go pricing as On-Demand, but at up to 90% off. EC2 can reclaim with a 2 minute warning. Best for stateless or fault tolerant workloads, and that additional scale capacity.
Over the last few years we have made significant changes to the spot pricing models. Each instance family and size, in each availability zone in every region is a separate spot pool, meaning that both price and capacity on each pool fluctuates infrequently and independently from each other; so if you use the same instance type on three different AZs you’re effectively consuming capacity from three different spot pools.

__Use combination of OnDemand with Spot instances__

__Convert Launch Configuration to Launch Template__

To benefits from above features, Autoscaling group must be launched with a launch template instead of a Launch Configuration.

## Prerequisites
You will need to have the latest version of the AWS CLI installed and configured before running the deployment script.
If you need help installing, please follow the link below:

[Installing the AWS CLI ](https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-install.html)

## Deployment for NEW_Microservices

Replace items written in <> with actual values.

1. Launch an ECS cluster using the Cloudformation template:

   ```
   $ aws cloudformation deploy \
   --template-file infrastructure/ecs.yml \
   --region <region> \
   --stack-name <stack name> \
   --capabilities CAPABILITY_NAMED_IAM \
   --tags Purpose=CostStrategiesDemo Project=NewMicroservices
   ```

2. Deploy the services onto your cluster:

   ```
   $ ./infrastructure/deploy.sh <region> <stack name>
   ```

3. Deploy the CloudWatch dashboard:
   ```
   $ ./infrastructure/deploy-cw-dashboard.sh <region> <stack name>
   ```

Load test this with your favourite load testing application.
You could also use, [Distributed Load Testing on AWS Solution](https://aws.amazon.com/solutions/implementations/distributed-load-testing-on-aws/) from AWS Solutions Library.

In my load test, I could see below
![CloudWatch Dashboard screenshot](../images/new-cloudwatch-dashboard.png)

## Load test Compute cost estimate

Region : US-WEST-1.
20 m4.large instances – On Demand, 20 m4.large instances – Spot. Consider constant use for a month.

20 instances x 0.117 USD On Demand hourly cost x 730 hrs in a month = 1708.00 USD
On-Demand instances (monthly): 1708.20 USD

Unit conversions: Spot discount*: 73/100 = 0.73
1708.20 USD - (1708.20 USD x 0.73) = 461.21 USD
Spot instances (monthly): 461.21 USD

**Total cost** (On Demand + Spot monthly): 2169.21 USD

**That was approx $400 less than previous sample, inspite of 10 additional instances.**

Further cost savings can be done by purchasing Savings plans. For example, the EC2 Instance Savings Plans rate for m4.large in the US West (N. California) for 1 Year term and All Upfront is 0.0851 USD

Reference -> [AWS Pricing Calculator](https://calculator.aws/#/)

Ultimately, our goal is to achieve long term cost optimization by implementing the strategies. For example, the cost explorer would eventually look like :
![Cost Explorer](../images/cost-explorer-cost-optimisation-trend.png)

Possible future upgrade :
![Reference architecture of microservices on EC2 Container Service with Fargate](../images/new-microservice-containers-ecs-fargate.png)

repository: gaonkarr/ECS-Cost-Strategies

gha_language: Shell

repo_name: gaonkarr/ECS-Cost-Strategies


text:
# ECOSBuilder

[![Build Status](https://travis-ci.org/JuliaOpt/ECOSBuilder.svg?branch=master)](https://travis-ci.org/JuliaOpt/ECOSBuilder)

This repository builds binary artifacts for the ECOSBuilder project. Binary artifacts are automatically uploaded to
[this repository's GitHub releases page](https://github.com/JuliaOpt/ECOSBuilder/releases) whenever a tag is created
on this repository.

This repository was created using [BinaryBuilder.jl](https://github.com/JuliaPackaging/BinaryBuilder.jl)

repository: JuliaOpt/ECOSBuilder

gha_language: Julia

repo_name: JuliaOpt/ECOSBuilder


text:
# switchboard
A wifi switchboard based on NodeMCU (ESP8266)

## Usage
Wire up GPIO pins of NodeMCU D0 to D7 to relay module inputs.
Change `config.lua` to configure the switch names, access point SSID and password and local hostname.
Upload the files to NodeMCU flash and start it up!

If everything goes well, you should see an access point available with the SSID you configured. There will be a server available which provides this API:

#### `GET` <IP_ADDRESS>
Returns the status of the device:
```json
{
    "status": "ok"
}
```

#### `GET` <IP_ADDRESS>/:id
Returns the state of the switch wired to the pin corresponding to the `id` (as specified in `config.lua`).

```json
{
    "state": 0
}
```

#### `POST` <IP_ADDRESS>/:id
Toggles the state of the switch wired to the pin corresponding to the `id` (as specified in `config.lua`).
```json
{
    "state": 1
}
```

**Note: You can also use `http://switchboard.local` (or whatever hostname you configured in `config.lua`) in place of `<IP_ADDRESS>`.**

repository: coditva/switchboard

repo_name: coditva/switchboard


text:
---
layout: post
title: "New exhibition to Orleans House Gallery 'Unsettling the Source of the Nile'"
permalink: /archives/2021/11/lbrut-new-exhibition-to-orleans-house-gallery-unsettling-the-source-of-the-nile.html
commentfile: 2021-11-04-lbrut-new-exhibition-to-orleans-house-gallery-unsettling-the-source-of-the-nile
category: around_town
date: 2021-11-04 10:00:00
image: "https://www.richmond.gov.uk/media/22686/source_of_the_nile_exhibition.jpg"
excerpt: |
  An exhibition of new images by Himali Singh Soin with historian of science  Alexis Rider will open at Orleans House Gallery on Friday, 19 November,  inspired by the collection of Sir Richard Burton.
---

An exhibition of new images by Himali Singh Soin with historian of science Alexis Rider will open at Orleans House Gallery on Friday, 19 November, inspired by the collection of Sir Richard Burton.

Sir Richard Burton's search for the source of the Nile is considered the epitome of nineteenth century Imperial exploration. However, the expedition is steeped in colonial notions of place and otherness. It is also the story of an environment that steadfastly resists being known. Alexis and Himali will interrogate Burton's search for the Nile. They will bring the river and its landscape, both real and imagined, to the foreground.

The exhibition presents a series of photographs that contain ghosts and shadows of the Burton collection. The images can be viewed alongside an accompanying text drawn from many sources, which offers an interpretive starting point for the images. Visitors are invited to explore archives, contested histories, and the nature of human and more-than-human relationships.

The exhibition will run from 19 November 2021 until 13 March 2022.

[Find out more about the exhibition](https://www.orleanshousegallery.org/events/himali-singh-soin-in-collaboration-with-alexis-rider/)

-- from a Richmond Council press release - 4 November 2021

repository: pmahnke/stmgrts

repo_name: pmahnke/stmgrts