{"id":16182424,"url":"https://github.com/drawveloper/act","last_synced_at":"2025-04-07T12:30:31.569Z","repository":{"id":148526197,"uuid":"245915830","full_name":"drawveloper/act","owner":"drawveloper","description":"A proof-of-concept CLI to manage Schemas and Configurations for Services.","archived":false,"fork":false,"pushed_at":"2020-05-17T23:38:39.000Z","size":15,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-02-13T15:18:12.302Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/drawveloper.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2020-03-09T01:11:53.000Z","updated_at":"2023-03-16T13:41:36.000Z","dependencies_parsed_at":"2023-05-20T10:00:19.375Z","dependency_job_id":null,"html_url":"https://github.com/drawveloper/act","commit_stats":null,"previous_names":["drawveloper/act"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/drawveloper%2Fact","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/drawveloper%2Fact/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/drawveloper%2Fact/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/drawveloper%2Fact/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/drawveloper","download_url":"https://codeload.github.com/drawveloper/act/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247652444,"owners_count":20973625,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-10-10T06:31:37.758Z","updated_at":"2025-04-07T12:30:31.492Z","avatar_url":"https://github.com/drawveloper.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# act - WORK IN PROGRESS\n\n\u003e *~think~ act different*\n\n*app config tree*  \n*automatic config tool*  \n*autonomy creates trust*  \n*alignment causes transformation*  \n*TODO: create a three-word image generator as WIP for act itself.*  \n\n`act` is a git-and-deno-based framework for distributed configuration management following the *code as configuration* pattern, inspired by [Facebook's `configerator`](https://research.fb.com/wp-content/uploads/2016/11/holistic-configuration-management-at-facebook.pdf) and VTEX IO [`apps and workspaces`](https://vtex.io/docs/concepts/workspace/).\n\n`act` proposes a mechanism to version and deploy inter-dependent configuration packages (*apps*) for distributed services. It does that by defining how these *apps* and *services* may relate to each other (e.g. *extend, configure, depend*) and providing tools to deploy, run and A/B test these services over time.\n\nYou can think of `act` as an opinionated toolset that allows organizations to safely evolve how arbitrarily large and complex systems act. While git is a low-level powertool to manage the state of a specific set of files, `act` wraps it (and deno) to implement a distributed and scalable end-to-end configuration management solution.\n\n## Getting started\n\n`act-cli` implements the lowest level API of operations to manage the state of an `act tenant`, which is an `act`-managed git repository. To start using `act`, simply create a GitHub repository and add it as a remote by using the command:\n\n```bash\n\u003e act login \u003corg\u003e/\u003crepo\u003e\n```\n\nThis will clone the repository locally into `~/.act/tenants/\u003corg\u003e/\u003crepo\u003e` and allow you to interact with this tenant, e.g. manage branches, install apps, deploy release trains, etc.\n\n`TODO: write detailed tutorial for getting started and link here. Should cover login, branch, install, build, deploy, merge.`\n\n## act apps and services\n\nApps are the building blocks of `act` - to the top-level user, they act as enablers of certain features, but they are actually more versatile. Formally, they are versioned packages of code-as-configuration for services. When a list of apps is compiled together, a given state is produced, which will be used by a service to dynamically decide it's behaviour.\n\nServices are running instances of *configurable* cloud software. They might be expressed in different languages and executed in multiple runtimes, but ultimately they respond to internet traffic and serve practical purposes. Services own their data and are independent - they provide a working functionality which is useful by itself, and that may change according to provided configuration. **Different configuration makes services act different**.\n\nApps declare four major hooks: builders (generate a versioned *build* from an *app source*), assemblers (generate a versioned *state* from a list of *builds*), runners (generate a response from a *request* and a given *state*) and *probers* (generate *status* from a list of *metrics*). Finally, they declare a *scorecard* which is the \"declaration of a desired future as measured by *probers*\". This allows them to create new *experiments*, consisting of proposed changes to configuration that would produce different outcomes (in terms of metrics).\n\n## Building apps\n\nApps are expressed as a collection of `.ts` TypeScript files, which are *securely* executed by a Deno service. Apps may use any safe Deno packages to help them build complex configuration. These files must export specific `act` classes to express the intended configuration that should be used when this particular app is installed.\n\nFor example, the list of installed apps in a tenant **is a** TypeScript file named `installed.ts` that exports a `Deno.App[]`. The contents of this array must implement the `Deno.App` class, that is in itself declared in a TypeScript file defined by each imported app. This allows for flexible emergence of patterns for advanced configuration generation while leveraging all the modern tooling used to create typed software.\n\nApp code (which describes how to generate configuration) *and the resulting generated config files* are both versioned in git repositories.\n\n## Publishing apps\n\nApps may be published to the `act registry` to allow for easy installation. The registry is actually a rewriter service for Github repositories, precisely like [deno.land/x/](https://deno.land/x/). This means publishing an app consists of creating a PR towards a centralized, versioned json file.\n\n## The act cli\n\nThe act cli offers basic commands to interact with two types of repos:\n\n- Tenant repo - represents the state of a tenant, which will ultimately express how services in a cloud infrastucture should act. This is where the state of installed apps is persisted and versioned.\n- App repo - represents the proposed configuration that is exercised when this app is installed in a tenant.\n\nAn app may further be divided in two types:\n\n- Services - declares a deployable service that responds to web traffic and may be configured by other apps.\n- Configs - declares configuration that affects the behaviour of running services. \n\n(Technically, Services are ultimately Configs that affect the behaviour of the native `act` services, but pragmatically it is useful to create the distinctions of whether an app defines a new functionality altogether or simply exports configuration. Services also tipically require more effort to deploy and rollback than Configs.)\n\n## Services are configured by apps\n\nServices express they are configurable by defining \"builders\" (a `service/builder` combination might be referred to simply as `builder`, imprecisely). These builders are functions which receive as arguments any content in this builder's \"folder\" in the app source and returns either a successful build and any output files, or an error. These files are appended to the app package before it is published to the registry.\n\nApps are versioned git repositories with a specific structure:\n\n- There is an app.ts definition file.\n- Every folder represents a `service` this exports some configuration to.\n- Every subsequent nested folder represents a `builder` in this service.\n- Any nested folder and files are offered as arguments to this `builder` during publish.\n\n## app.ts example file\n\n```ts\nimport { App } from 'https://act.pm/std/1/app.ts'\n\nexport default new App({\n  ...\n})\n```\n\nGenerated config:\n\n```json\n{\n  \"publisher\": \"act\",\n  \"name\": \"calculator\",\n  \"version\": \"4.2.0\",\n  \"description\": \"\",\n  \n  \"bugs\": \"URL\",\n  \"repository\": {},\n  \"contributors\": [],\n\n  \"extends\": \"\",\n  \"configures\": {},\n  \"depends\": {},\n}\n```\n\n## Tenants manage branches of installed apps\n\nApps are only useful when they are installed to a `tenant branch`. This allows services to act differently when given access to the service state generated by assembling the apps installed in this branch.\n\n## TODO: Calculator service example\n\nFor example, if app `act.calculator@4` wants to configure the `router` service `http` builder, ...\n\n## TODO: act native services\n\nThere are three basic services which offer the baseline for the creation of custom services:\n\n### Builder\n\nReceives app source as parameter. Outputs are appended to published package.\n\n### Assembler\n\nReceives list of built packages as parameter. Outputs service state.\n\n### Runner\n\nA runner is a docker image with a server which receives requests with a service state hash.\n\n## TODO:  Three relationships - extend, configure, depend\n\n### Apps extend Apps\n\nExtend allows to inherit exported configurations and override them selectively (IS A applies). e.g. gtm extends pixel (which configures render).\n\n### Apps configure Services\n\nPackaged configuration is used to generate service state and ultimately impact service behaviour.\n\n### Services depend on Services\n\nStatic services calculate responses from request params and service state solely, but dynamic services might require I/O to other running services. This constitutes a runtime dependency.\n\n## TODO: Router example\n\n`act-router` implements a the `router` service, which routes requests based on state generated by it's `http` builder. This allows other services to request routes by exporting configuration for this builder.\n\nBy doing so, every service that wants to claim a new route must go through the process of publishing an *app* - a versioned package of configuration - and later generating a new versioned state for the `router`, which might be on-demand or scheduled - depending on how you configure it.\n\nThese configuration changes then go through e2e testing in a production-like environment and are then gradually distributed to live `router` instances. If any of the service-defined success metrics are disturbed according to ML-enabled projection, we automatically reverse to previous state and alert configuration publishers, resuming previous behaviour without human interaction.\n\nThis allows to maximize iteration speed on configuration tests without compromising on user experience. Move fast without breaking things, as a service.\n\n## (Historical, probably will be removed or heavily modified) Motivation\n\nAct is a proof-of-concept CLI to manage **Schemas** and **Configurations** for **Services**.\n\n### Services, Behaviors and Outcomes\n\nWhen an *Enterprise* deploys *Services* (in the form of software) which their *Users* interact with, we can assume it has two basic goals:\n\n1. That their Users have a high-quality, disruption-free user experience when interacting with said *Services*, and\n2. That these interactions result in *Outcomes* which are desireable for the *Enterprise* (e.g. new sales).\n\nIn other words, a software platform is successful to the degree that it helps transform a collections of *Services* into desired business *Outcomes*.\n\n*Outcomes* are not deterministic, since they depend on user decisions. However, *Outcomes* may be significantly influenced by changing a Service's *Behaviour* - the way in which the Service responds to *Input*.\n\nMost Services offer some degree of control over their Behavior through *Configuration*. That means an Enterprise may alter the *Behavior* of the Services it controls by changing their *Configurations*, which in turn affects *Outcomes*.\n\nConfigurable Services need to define a *Schema*, a *Semantically Versioned* contract, through which they explicitly document *how* they can be configured.\n\n#### Definitions\n\n- A **Service** is any business capability packaged as software which displays consistent *Behavior* when interacting with the outside world (Users or other Services).\n- A **Behavior** is the way in which a Service responds to external Input, or otherwise acts. A Behavior is usually determined, at least partially, by *Configuration*.\n- An **Outcome** is a business goal which depends on *Users* interacting with *Services* (and their *Behaviors*).\n- A **Configuration** is any artifact which deterministically alters the Behavior of a Service. A Configuration must follow a *Schema*.\n- A **Schema** is any Service-define artifact against which any Configuration might be *Validated* in order to determine if said configuration is usable by the Service. In other words, Schemas define which Configurations are valid for a given Service.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdrawveloper%2Fact","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdrawveloper%2Fact","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdrawveloper%2Fact/lists"}