Autonomía digital y tecnológica

Código e ideas para una internet distribuida

Linkoteca. desarrollo web

the CSS fonts spec has a couple (new to me) generic font families, like ui-serif and ui-sans-serif, aimed at providing finer-grained controls for specifying OS-level fonts. This allows developers the power to integrate their UIs with the look and feel of the underlying operating system. To suggest Apple user agents render text on screen with the “New York” serif font, developers can specify: font-family: ui-serif.

The namespace conception in HTML is similar to other web languages; it prevents ambiguity on the data structure. It refers to which semantic vocabularies or syntax should be used when the namespace is present in the document. In our case, the og namespace refers to the Open Graph Protocol, while the fb namespace refers to Facebook-own Open Graph specification.

Alternatively, we can use the prefix attribute to define these namespaces.

Twitter card tags look similar to Open Graph tags, and are based on the same conventions as the Open Graph protocol. When using Open Graph protocol to describe data on a page, it is easy to generate a Twitter card without duplicating tags and data. When the Twitter card processor looks for tags on a page, it first checks for the Twitter-specific property, and if not present, falls back to the supported Open Graph property. This allows for both to be defined on the page independently, and minimizes the amount of duplicate markup required to describe content and experience.

Note that while Open Graph recommends specifying the “og” RDFa Core 1.1 CURIE prefix mapping via, no such markup is required for Twitter cards and its use of the twitter: prefix in a HTML meta element’s name attribute. Open Graph protocol also specifies the use of property and content attributes for markup () while Twitter cards use name and content. Twitter’s parser will fall back to using property and content, so there is no need to modify existing Open Graph protocol markup if it already exists.

The example below uses a mix of Twitter and Open Graph tags to define a summary card:

Luckily, our favorite social networks also provide tools to help us debug our tags. Once you make sure that your tags are actually showing up in the source code of your website, you’ll be able to preview how your website will look in the feed.


Specify the type of commit:

feat: The new feature you’re adding to a particular application
fix: A bug fix
style: Feature and updates related to styling
refactor: Refactoring a specific section of the codebase
test: Everything related to testing
docs: Everything related to documentation
chore: Regular code maintenance.[ You can also use emojis to represent commit types]

Separate the subject from the body with a blank line
Your commit message should not contain any whitespace errors
Remove unnecessary punctuation marks
Do not end the subject line with a period
Capitalize the subject line and each paragraph
Use the imperative mood in the subject line
Use the body to explain what changes you have made and why you made them.
Do not assume the reviewer understands what the original problem was, ensure you add it.
Do not think your code is self-explanatory
Follow the commit convention defined by your team

OpenID is about authentication (ie. proving who you are), OAuth is about authorisation (ie. to grant access to functionality/data/etc.. without having to deal with the original authentication).

OAuth could be used in external partner sites to allow access to protected data without them having to re-authenticate a user.

The blog post «OpenID versus OAuth from the user’s perspective» has a simple comparison of the two from the user’s perspective and «OAuth-OpenID: You’re Barking Up the Wrong Tree if you Think They’re the Same Thing» has more information about it.

BEM — Block Element Modifier is a methodology that helps you to create reusable components and code sharing in front-end development.

BEM is a highly useful, powerful, and simple naming convention that makes your front-end code easier to read and understand, easier to work with, easier to scale, more robust and explicit, and a lot more strict.

The BEM approach ensures that everyone who participates in the development of a website works with a single codebase and speaks the same language. Using BEM’s proper naming convention will better prepare you for design changes made to your website.

PyPI packages not in the standard library:

  • virtualenv is a very popular tool that creates isolated Python environments for Python libraries. If you’re not familiar with this tool, I highly recommend learning it, as it is a very useful tool, and I’ll be making comparisons to it for the rest of this answer.

    It works by installing a bunch of files in a directory (eg: env/), and then modifying the PATH environment variable to prefix it with a custom bin directory (eg: env/bin/). An exact copy of the python or python3 binary is placed in this directory, but Python is programmed to look for libraries relative to its path first, in the environment directory. It’s not part of Python’s standard library, but is officially blessed by the PyPA (Python Packaging Authority). Once activated, you can install packages in the virtual environment using pip.

  • pyenv is used to isolate Python versions. For example, you may want to test your code against Python 2.7, 3.6, 3.7 and 3.8, so you’ll need a way to switch between them. Once activated, it prefixes the PATH environment variable with ~/.pyenv/shims, where there are special files matching the Python commands (python, pip). These are not copies of the Python-shipped commands; they are special scripts that decide on the fly which version of Python to run based on the PYENV_VERSION environment variable, or the .python-version file, or the ~/.pyenv/version file. pyenv also makes the process of downloading and installing multiple Python versions easier, using the command pyenv install.
  • pyenv-virtualenv is a plugin for pyenv by the same author as pyenv, to allow you to use pyenv and virtualenv at the same time conveniently. However, if you’re using Python 3.3 or later, pyenv-virtualenv will try to run python -m venv if it is available, instead of virtualenv. You can use virtualenv and pyenv together without pyenv-virtualenv, if you don’t want the convenience features.
  • virtualenvwrapper is a set of extensions to virtualenv (see docs). It gives you commands like mkvirtualenv, lssitepackages, and especially workon for switching between different virtualenv directories. This tool is especially useful if you want multiple virtualenv directories.
  • pyenv-virtualenvwrapper is a plugin for pyenv by the same author as pyenv, to conveniently integrate virtualenvwrapper into pyenv.
  • pipenv aims to combine Pipfile, pip and virtualenv into one command on the command-line. The virtualenv directory typically gets placed in ~/.local/share/virtualenvs/XXX, with XXX being a hash of the path of the project directory. This is different from virtualenv, where the directory is typically in the current working directory. pipenv is meant to be used when developing Python applications (as opposed to libraries). There are alternatives to pipenv, such as poetry, which I won’t list here since this question is only about the packages that are similarly named.

Standard library:

  • pyvenv is a script shipped with Python 3 but deprecated in Python 3.6 as it had problems (not to mention the confusing name). In Python 3.6+, the exact equivalent is python3 -m venv.
  • venv is a package shipped with Python 3, which you can run using python3 -m venv (although for some reason some distros separate it out into a separate distro package, such as python3-venv on Ubuntu/Debian). It serves the same purpose as virtualenv, but only has a subset of its features (see a comparison here). virtualenv continues to be more popular than venv, especially since the former supports both Python 2 and 3.

Recommendation for beginners:

This is my personal recommendation for beginners: start by learning virtualenv and pip, tools which work with both Python 2 and 3 and in a variety of situations, and pick up other tools once you start needing them.

The async and await keywords are a great addition to Javascript. They make it easier to read (and write) code that runs asynchronously. That includes things like:

API calls (using fetch or a library like axios);
Timeouts (though these need a little extra work); or
Reading/writing files if you’re using NodeJS.

I’m going to assume you’re familiar with Promises and making a simple async/await call. Where it can get tricky is when we have a whole bunch of tasks in an array. You might run through the array expecting calls to run one-by-one. But instead, they run through all together and don’t wait for each individual item to resolve. Or, you might find yourself with the opposite problem. You run through your array in a loop, wanting them to run in parallel. But instead, it waits and does them one by one. And sometimes, you try something and it doesn’t work at all. The program just continues after the loop instead of waiting until the calls are all done. You end up wondering if there’s something you’re missing.

Promises simplify deferred and asynchronous computations. A promise represents an operation that hasn’t completed yet.

A promise can be:

fulfilled – The action relating to the promise succeeded
rejected – The action relating to the promise failed
pending – Hasn’t fulfilled or rejected yet
settled – Has fulfilled or rejected

Essentially, a promise is a returned object to which you attach callbacks, instead of passing callbacks into a function.

A common need is to execute two or more asynchronous operations back to back, where each subsequent operation starts when the previous operation succeeds, with the result from the previous step. We accomplish this by creating a promise chain.

Promises solve a fundamental flaw with the callback pyramid of doom, by catching all errors, even thrown exceptions and programming errors. This is essential for functional composition of asynchronous operations.

Not too long ago I decided to write a jQuery plugin for making the use of iScroll a little less painful. Since I made the plugin at work I’m not really at liberty to share it. But what I can share is a step by step tutorial for creating a jQuery plugin of your own. Let’s get started.

virtualenvwrapper is a set of extensions to Ian Bicking’s virtualenv tool. The extensions include wrappers for creating and deleting virtual environments and otherwise managing your development workflow, making it easier to work on more than one project at a time without introducing conflicts in their dependencies.

Organizes all of your virtual environments in one place.
Wrappers for managing your virtual environments (create, delete, copy).
Use a single command to switch between environments.
Tab completion for commands that take a virtual environment as argument.
User-configurable hooks for all operations (see Per-User Customization).
Plugin system for creating more sharable extensions (see Extending Virtualenvwrapper).

Well, a virtual environment is just a directory with three important components:

A site-packages/ folder where third party libraries are installed.
Symlinks to Python executables installed on your system.
Scripts that ensure executed Python code uses the Python interpreter and site packages installed inside the given virtual environment.

(venv) % pip freeze

And write the output to a file, which we’ll call requirements.txt.

(venv) % pip freeze > requirements.txt

Duplicating Environments

Sara% cd test-project/
Sara% python3 -m venv venv/
(venv) Sara% pip install -r requirements.txtCollecting numpy==1.15.3 (from -r i (line 1))
Installing collected packages: numpy
Successfully installed numpy-1.15.3

…python -m pip executes pip using the Python interpreter you specified as python. So /usr/bin/python3.7 -m pip means you are executing pip for your interpreter located at /usr/bin/python3.7.

But when you use python -m pip with python being the specific interpreter you want to use, all of the above ambiguity is gone. If I say python3.8 -m pip then I know pip will be using and installing for my Python 3.8 interpreter (same goes for if I had said python3.7).

While we’re on the subject of how to avoid messing up your Python installation, I want to make the point that you should never install stuff into your global Python interpreter when you. develop locally (containers are a different matter)! If it’s your system install of Python then you may actually break your system if you install an incompatible version of a library that your OS relies on.

Building a truly international application is not just about translating strings. Other issues to consider are date and time formats, currency symbols and pluralization. Programmers often underestimate the complexity of localization and get stuck with homemade code that is a pain to maintain. So, let’s talk about PHP Arrays, gettext, frameworks, and Intl.

First I take the whole CSV file and split it into an array of lines. Then, I take the first line, which should be the headers, and split that by a comma into an array. Then, I loop through all the lines (skipping the first one) and inside, I loop through the headers and assign the values from each line to the proper object parameters. At this point, you probably want to just return the JavaScript object, but you can also JSON.stringify the result and return the JSON object.

A pretty specific title, huh? The versioning is key in this map-making how-to. D3.js version 5 has gotten serious with the Promise class which resulted in some subtle syntax changes that proven big enough to cause confusion among the D3.js old dogs and the newcomers. This post guides you through creating a simple map in this specific version of the library. If you’d rather dive deeper into the art of making maps in D3 try the classic guides produced by Mike Bostock.

A specification for adding human and machine readable meaning to commit messages.

The Conventional Commits specification is a lightweight convention on top of commit messages. It provides an easy set of rules for creating an explicit commit history; which makes it easier to write automated tools on top of. This convention dovetails with SemVer, by describing the features, fixes, and breaking changes made in commit messages.

The Customizer Export/Import plugin allows you to export or import your WordPress customizer settings from directly within the customizer interface! If your theme makes use of the WordPress customizer for its settings, this plugin is for you!

To create a «polls» app in the «apps» sub-directory, do the following first to make the directory (assuming you are at the root of your django project):

mkdir apps/polls

Next, run startapp to create «polls» in under the «app» project directory.

startapp polls apps/polls

Install the app;



makemigrations polls


urlpatterns = [

Captura de pantalla de

welcome to the year 2030.
there are 1.2 billion more people on the planet.
70% of us are living in cities now.
in order to house 1.2 billion more people,
all of us are sharing more household goods and services than ever before.
we refer to this sharing as co-living.
and many more of us are living this way now.

but it’s not a new thing.
communal living has always been a solution to common problems.
like rapid urbanisation, loneliness, and high living costs.
but what does co-living look like in the year 2030?
who is it for?
how has it changed our society?
what are we sharing?

with many more of us now co-living,
there is no one configuration.
discover what type of co-living would be uniquely suited for you.
reserve your spot for ONE SHARED HOUSE 2030.

REM to PX Converter is a free online tool you can use to easily convert rem (root em) to px (pixel). Keep in mind that 1rem is equal to the root font-size, in other words, the font-size on element.