-
-
Save codenameyau/9f0a26a0f1be35a6784a to your computer and use it in GitHub Desktop.
/************************************************************************ | |
* CLIENT ONE-LINERS | |
*************************************************************************/ | |
// Set top level domain cookie. | |
document.cookie = "token=12345; Max-Age=120; Secure; Domain=mozilla.org; Path=/;" | |
// Set a subdomain cookie. | |
document.cookie = "name=hello world; Max-Age=120; Secure; Domain=developer.mozilla.org; Path=/;" | |
// You can have cookies with the same name but with different paths and domains. | |
document.cookie = "name=1; Max-Age=60; Secure; Domain=mozilla.org;" | |
document.cookie = "name=2; Max-Age=60; Secure; Domain=mozilla.org; Path=/" | |
document.cookie = "name=3; Max-Age=60; Secure; Domain=developer.mozilla.org; Path=/;" | |
// Copies variable. | |
copy(temp1) | |
copy(JSON.stringify(temp1)) | |
// Capture regex groups with variable | |
const string = 'ayyyy lmao' | |
const rgx = /(?<firstVowel>[aeiou])/ | |
string.match(rgx).groups.firstVowel | |
// Copies current selection to clipboard. | |
// https://developer.mozilla.org/en-US/docs/Web/API/Document/execCommand | |
// https://hackernoon.com/copying-text-to-clipboard-with-javascript-df4d4988697f | |
document.execCommand('copy') | |
// Copies text content of click to clipboard. | |
navigator.clipboard && navigator.clipboard.writeText(event.target.textContent); | |
// Makes page text editable. | |
document.designMode = 'on' | |
// Access third party frames on window. | |
window.frames | |
// Create bookmark and set this to URL to skip ads. | |
javascript:void(document.querySelector('video').currentTime = document.querySelector('video').duration) | |
// See all event listeners. Remember to remove listener when unmounting. | |
getEventListeners(document) | |
// See Slack Emoji authors. | |
Array.from(document.querySelectorAll('.author_cell > a')).map((a) => a.text.trim()).sort() | |
// Use this to click all links. | |
Array.from(document.querySelectorAll('a.block')).forEach(a => a.click()) | |
// Grab all the images from a page (namely instagram) | |
Array.from(document.images).forEach(img => console.log(img.getAttribute('src'))) | |
// Like all facebook posts. | |
Array.from(document.body.querySelectorAll('.UFILikeLink')).forEach((a) => a.click()) | |
// Selecting wildcard classes. | |
Array.from(document.querySelectorAll('div[class^="ManageSection__column-left"] .dp-checkbox')).forEach((a) => a.click()) | |
/************************************************************************ | |
* SERVER ONE-LINERS | |
*************************************************************************/ | |
// Use Now to deploying static app serving a single page app. | |
ns ./build --cmd 'list ./content -s' |
// Checks if nested property exists. | |
db.drafts.find({"collection_type": "web_advertising", "email": "jorge@email.com", "rows.222": { $exists: true } }); | |
// Grabs the count. | |
db.drafts.find({"email": "jorge@email.com"}).count(); |
/******************************************************************** | |
* UTILS | |
*********************************************************************/ | |
// https://stackoverflow.com/q/779379 | |
setTimeout(function (callback) { | |
// Offload Heavy computation. | |
}, 0); | |
/******************************************************************** | |
* JQUERY serializeArray | |
*********************************************************************/ | |
// Converts form into Array of Objects. | |
// https://plainjs.com/javascript/ajax/serialize-form-data-into-an-array-46/ | |
function serializeArray(form) { | |
var field, l, s = []; | |
if (typeof form == 'object' && form.nodeName == "FORM") { | |
var len = form.elements.length; | |
for (var i = 0; i < len; i++) { | |
field = form.elements[i]; | |
if (field.name && !field.disabled && field.type != 'file' && field.type != 'reset' && field.type != 'submit' && field.type != 'button') { | |
if (field.type == 'select-multiple') { | |
l = form.elements[i].options.length; | |
for (j = 0; j < l; j++) { | |
if (field.options[j].selected) | |
s[s.length] = { | |
name: field.name, | |
value: field.options[j].value | |
}; | |
} | |
} else if ((field.type != 'checkbox' && field.type != 'radio') || field.checked) { | |
s[s.length] = { | |
name: field.name, | |
value: field.value | |
}; | |
} | |
} | |
} | |
} | |
return s; | |
} | |
// Nodejs check if module is called directly | |
const CALLED_DIRECTLY = require.main === module; | |
function splitTextarea(text) { | |
return text.trim().replace(/\s+/, '\n').replace(/\n{2,}/, '').split('\n'); | |
} | |
// Download using fetch API.. | |
import download from 'downloadjs'; | |
const handleBufferDownload = (filename) => { | |
res.arrayBuffer() | |
.then((buffer) => { | |
download(buffer, filename, contentType); | |
stopLoading(); | |
}); | |
}; | |
// http://stackoverflow.com/a/23842171 | |
encodeURIComparison = function() { | |
var arr = []; | |
for(var i=0; i<256; i++) { | |
var char=String.fromCharCode(i); | |
if(encodeURI(char) !== encodeURIComponent(char)) { | |
arr.push({ | |
character: char, | |
encodeURI: encodeURI(char), | |
encodeURIComponent: encodeURIComponent(char) | |
}); | |
} | |
} | |
console.table(arr); | |
}; | |
function encodeQueryParams (url, queryParams) { | |
return Object.keys(queryParams).reduce((a, key) => { | |
a.push(key + '=' + encodeURIComponent(queryParams[key])); | |
return a; | |
}, []).join('&'); | |
} | |
let queryString = encodeQueryParams(queryParams); | |
url += url.indexOf('?') > -1 ? '&' : '?' + queryString; | |
/******************************************************************** | |
* JQUERY COLOR CONTRAST | |
*********************************************************************/ | |
jQuery.Color.fn.contrastColor = function() { | |
var r = this._rgba[0], g = this._rgba[1], b = this._rgba[2]; | |
return (((r*299)+(g*587)+(b*144))/1000) >= 131.5 ? "black" : "white"; | |
}; | |
// usage examples: | |
jQuery.Color("#bada55").contrastColor(); // "black" | |
element.css( "color", jQuery.Color( element, "backgroundColor" ).contrastColor() ); | |
Event Tracking
We use Google Tag Manager to manage our third-party integrations and trackers. To get started you should create a new Google Tag Manager account and ask for access to "Stash Invest" and "app.stashinvest.com".
Events are fired in our redux middleware in middleware/events.js
. Make sure to publish your tag!!!
Triggers
In the Tag Manager UI, you can create a trigger to listen for events which you can fire with this code snippet.
const eventName = 'Transaction';
const eventProperties = {
origin: window.location.pathname
};
window.dataLayer.push(eventName, eventProperties);
Tags
After you create a trigger, you can create a Tag. Choose Custom HTML and insert a code snippet.
Mixpanel Example
<script>
window.mixpanel && window.mixpanel.track('Transaction', {{DataLayer properties}})
</script>
Marketing Pixel Example
<script>
(function() {
function uuidv4() {
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {
var r = Math.random() * 16 | 0, v = c == 'x' ? r : (r & 0x3 | 0x8);
return v.toString(16);
});
}
var uuid = uuidv4();
var iframe = document.createElement("iframe");
iframe.style.visibility = 'hidden';
iframe.style.position = 'absolute';
iframe.style.left = '-9000px';
iframe.src = "https://example.com" + uuid;
iframe.width = "1";
iframe.height = "1";
document.body.appendChild(iframe);
})()
</script>
Google Pixel
<script>
/* <![CDATA[ */
var google_conversion_id = 0;
var google_conversion_label = "";
var google_remarketing_only = false;
/* ]]> */
(function() {
var properties = {{DataLayer properties}};
if (properties && properties.Action === 'On') {
var s = document.createElement('script');
s.async = true;
s.src = '//www.googleadservices.com/pagead/conversion.js';
var h = document.getElementsByTagName('head')[0];
h.appendChild(s);
}
})();
</script>
Dynamic Script Example
<script>
(function() {
var s = document.createElement('script');
s.async = true;
s.src = '//cdn.nanigans.com/NaN_tracker.js';
var h = document.getElementsByTagName('head')[0];
h.appendChild(s);
})();
</script>
Publish
Click Publish and test your code locally. GTM allows you to push your changes to two "environments":
- Live will push changes to production (app.stashinvest.com)
- Latest will push changes to all other environments (Local, Edge and Staging)
Tips
⚠️ Watch out for quotes. Make sure to use actual quotes instead of MS Word quotes.
Utils
const isMobileThunk = () => {
let cachedValue;
return () => {
if (cachedValue === undefined) {
let check = false;
(function(a) {
if (/(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows ce|xda|xiino/i.test(a) || /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw-(n|u)|c55\/|capi|ccwa|cdm-|cell|chtm|cldc|cmd-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc-s|devi|dica|dmob|do(c|p)o|ds(12|-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(-|_)|g1 u|g560|gene|gf-5|g-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd-(m|p|t)|hei-|hi(pt|ta)|hp( i|ip)|hs-c|ht(c(-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i-(20|go|ma)|i230|iac( |-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|-[a-w])|libw|lynx|m1-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|-([1-8]|c))|phil|pire|pl(ay|uc)|pn-2|po(ck|rt|se)|prox|psio|pt-g|qa-a|qc(07|12|21|32|60|-[2-7]|i-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h-|oo|p-)|sdk\/|se(c(-|0|1)|47|mc|nd|ri)|sgh-|shar|sie(-|m)|sk-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h-|v-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl-|tdg-|tel(i|m)|tim-|t-mo|to(pl|sh)|ts(70|m-|m3|m5)|tx-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas-|your|zeto|zte-/i.test(a.substr(0, 4))) check = true;
})(navigator.userAgent || navigator.vendor || window.opera);
cachedValue = check;
}
return cachedValue;
};
}
export const isMobile = isMobileThunk();
export const isMacintosh = () => {
return navigator.platform.indexOf('Mac') > -1
}
export const isWindows = () => {
return navigator.platform.indexOf('Win') > -1
}
export const serialize = (queryParams) => {
const params = [];
for (let param in queryParams) {
if (queryParams.hasOwnProperty(param)) {
params.push(encodeURIComponent(param) + "=" + encodeURIComponent(queryParams[param]));
}
}
return params.join("&");
}
export const pathOr = (defaultVal, paths, obj) => {
let val = obj;
let index = 0;
while (index < paths.length) {
if (val == null) {
return defaultVal;
}
val = val[paths[index]]
index++;
}
return val == null ? defaultVal : val;
}
Code highlights
const GLTR_ID = tickers['GLTR'] && tickers['GLTR'].card_id;
const VNQ_ID = tickers['VNQ'] && tickers['VNQ'].card_id;
const hasInvestmentInAnyAccount = (cardIds) => {
return Object.values(accounts).some((account) => {
return account.cards && cardIds.some((cardId) => {
return account.cards[cardId];
});
})
}
hasInvestmentInAnyAccount([GLTR_ID, VNQ_ID])
Fetch redux thunk helper
middleware/request.js
export const encodeQuery = (query) => {
return Object.keys(query).reduce((a, key) => {
a.push(key + '=' + encodeURIComponent(query[key]));
return a;
}, []).join('&');
}
export const httpOptions = {
method: 'GET',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
}
};
export const request = async (dispatch, getState, config) => {
const {actions, path, query, options} = config;
// Parse query string options and add to url.
const url = query ? '?' + encodeQuery(query) : path;
// Stringify request body.
options.body = options.body && JSON.stringify(options.body);
const fetchOptions = {
...httpOptions,
...options,
}
actions.request && dispatch({
type: actions.request
});
const res = await fetch(url, fetchOptions);
if (res.status >= 400) {
const json = await res.json();
actions.error && dispatch({
type: actions.error,
status: res.status,
body: json,
})
}
const contentType = res.headers.get('Content-Type');
if (contentType.indexOf('application/json') > -1) {
const json = await res.json();
actions.success && dispatch({
type: actions.success,
status: res.status,
body: json
});
}
if (contentType.indexOf('text/html') > -1) {
await res.text();
actions.success && dispatch({
type: actions.success,
status: res.status,
});
}
};
export default request;
middleware/index.js
/**
* Read more about middleware here:
* http://redux.js.org/docs/advanced/Middleware.html
*/
import { applyMiddleware } from 'redux';
import { composeWithDevTools } from 'redux-devtools-extension';
import thunk from './thunk';
import request from './request';
const middleware = [
thunk.withExtraArgument(request),
];
if (process.env.NODE_ENV === 'development') {
const { logger } = require('redux-logger');
middleware.push(logger);
}
export default composeWithDevTools(applyMiddleware(...middleware));
export const PATCH_EXPERIMENT_REQUEST = 'PATCH_EXPERIMENT_REQUEST';
export const PATCH_EXPERIMENT_SUCCESS = 'PATCH_EXPERIMENT_SUCCESS';
export const PATCH_EXPERIMENT_ERROR = 'PATCH_EXPERIMENT_ERROR';
export const patchExperiment = ({ version, active, experiment_urls }) => {
return (dispatch, getState, request) => {
return request(dispatch, getState, {
actions: {
request: PATCH_EXPERIMENT_REQUEST,
success: PATCH_EXPERIMENT_SUCCESS,
error: PATCH_EXPERIMENT_ERROR
},
path: `/api/experiment/${version}`,
options: {
method: 'PATCH',
body: {
active,
experiment_urls
}
}
});
}
}
Tooling and Build
Compiling ES6 with Babel CLI
# Babel CLI should be installed locally rather than globally.
npm install --save-dev babel-cli
# Compile or watch a particular file.
babel public/scripts/snake.js -o public/scripts/snake-es5.js
babel public/scripts/snake.js -o public/scripts/snake-es5.js --watch
White-transparent gradient
const Wrapper = styled.div`
width: 100%;
position: relative;
@media (max-width: 768px) {
&::before {
content: '';
background: linear-gradient(to bottom, white, transparent);
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 50px;
z-index: 1;
margin-top: -25px;
}
}
`;
VSCode debugger with CRA tests
Sell bots
https://botbroker.io/bots
{
// Use IntelliSense to learn about possible attributes.
// Hover to view descriptions of existing attributes.
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"name": "Debug CRA Tests",
"type": "node",
"request": "launch",
"runtimeExecutable": "${workspaceRoot}/node_modules/.bin/react-scripts",
"args": ["test", "${relativeFile}", "--no-cache", "--modulePaths=src"],
"env": { "CI": "true" },
"cwd": "${workspaceRoot}",
"protocol": "inspector",
"console": "integratedTerminal",
"internalConsoleOptions": "neverOpen"
}
]
}
Mocking modules
jest.mock('stash/utils/experiments.js', function() {
return {
startExperiment: jest.fn(res => {
return 0;
}),
};
});
import * as utils from 'stash/utils';
utils.isMobile = jest.fn().mockReturnValue(true);
Opening chrome with CORS disabled
open -n -a /Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome --args --user-data-dir="/tmp/chrome_dev_test" --disable-web-security
Mongo DB data migration
Binary
# Import database
mongorestore -h ds141168.mlab.com:41168 -d heroku_nl79h610 -u <user> -p <password> <input db directory>
# Export database
mongodump -h ds141168.mlab.com:41168 -d heroku_nl79h610 -u <user> -p <password> -o <output directory>
# Import collection
mongorestore -h ds141168.mlab.com:41168 -d heroku_nl79h610 -u <user> -p <password> <input .bson file>
# Export collection
mongodump -h ds141168.mlab.com:41168 -d heroku_nl79h610 -c <collection> -u <user> -p <password> -o <output directory>
JSON
# Import collection
mongoimport -h ds141168.mlab.com:41168 -d heroku_nl79h610 -c <collection> -u <user> -p <password> --file <input file>
# Export collection
mongoexport -h ds141168.mlab.com:41168 -d heroku_nl79h610 -c <collection> -u <user> -p <password> -o <output file>
CSV
# Import collection
mongoimport -h ds141168.mlab.com:41168 -d heroku_nl79h610 -c <collection> -u <user> -p <password> --file <input .csv file> --type csv --headerline
# Export collection
mongoexport -h ds141168.mlab.com:41168 -d heroku_nl79h610 -c <collection> -u <user> -p <password> -o <output .csv file> --csv -f <comma-separated list of field names>
Tree rendering in React
touchstart event