1.3.1 • Published 4 months ago
effect-octokit-layer v1.3.1
effect-octokit-layer
An Effect layer to interact with Github Octokit api.
⚡ Access to github api
You first need to create a github token with a scope related to your needs.
GITHUB_TOKEN="my-github-token"
⚡ Layer Api
🔶 Layer functions Types
The layer exposes functions with the following type:
import type { ConfigError, Effect } from 'effect';
type LayerErrors = GithubApiError | ApiRateLimitError | ConfigError.ConfigError;
type LoggerLayer = {
warn: (
message?: unknown,
...optionalParams: unknown[]
) => Effect.Effect<void>;
};
type LayerFunction<TArgs, TResult> = (
args: TArgs
) => Effect<TResult, LayerErrors, LoggerLayer>;
For example, getting user profile can be done with this function:
type GetUserProfile = (
username: string
) => Effect<UserProfileResult, LayerErrors, Logger>;
🔶 Users
import {
OctokitLayer,
OctokitLayerLive,
LoggerConsoleLive,
} from 'effect-octokit-layer';
const username = 'jpb06';
const [profile, repos, orgs, events] = await Effect.runPromise(
pipe(
Effect.all(
[
// Get user profile
OctokitLayer.user(username).profile(),
// Get user repos
OctokitLayer.user(username).repos(),
// Get user organizations
OctokitLayer.user(username).orgs(),
// Get user events
OctokitLayer.user(username).events(),
],
// Fetch all these in parallel
{ concurrency: 'unbounded' }
),
Effect.provide(Layer.mergeAll(OctokitLayerLive, LoggerConsoleLive))
)
);
🔶 Organizations
import {
OctokitLayer,
OctokitLayerLive,
LoggerConsoleLive,
} from 'effect-octokit-layer';
const orgs = await Effect.runPromise(
pipe(
// Get organization repos
OctokitLayer.org('my-org').repos(),
Effect.provide(Layer.mergeAll(OctokitLayerLive, LoggerConsoleLive))
)
);
🔶 Repositories
import {
RepoArgs,
OctokitLayer,
OctokitLayerLive,
LoggerConsoleLive,
} from 'effect-octokit-layer';
const reactRepo: RepoArgs = {
owner: 'facebook',
name: 'react',
};
const [issues, pulls, issue34] = await Effect.runPromise(
pipe(
Effect.all(
[
// Get all issues
OctokitLayer.repo(reactRepo).issues(),
// Get all pull requests
OctokitLayer.repo(reactRepo).pulls(),
// Get issue #34
OctokitLayer.repo(reactRepo).issue(34),
],
// Fetch all these in parallel
{ concurrency: 'unbounded' }
),
Effect.provide(Layer.mergeAll(OctokitLayerLive, LoggerConsoleLive))
)
);
🔶 Pull requests
import {
RepoArgs,
OctokitLayer,
OctokitLayerLive,
LoggerConsoleLive,
} from 'effect-octokit-layer';
const reactRepo: RepoArgs = {
owner: 'facebook',
name: 'react',
};
const pull = repo.pull(39);
const [details, comments, reviews, createdReview, deletedReview] = await Effect.runPromise(
pipe(
Effect.all(
[
// Pull request details
pull.details(),
// All the comments made on the pull request #39
pull.comments(),
// Pull request #39 reviews
pull.reviews.get(),
// Create a review
pull.reviews.create({
event: 'REQUEST_CHANGES',
body: 'I think some points need to be adressed',
comments: [{
path: './src/cool.ts',
body: "Shouldn't this file be renamed",
}],
}),
// Delete review #2
pull.reviews.delete(2);
],
{ concurrency: 'unbounded' }
),
Effect.provide(Layer.mergeAll(OctokitLayerLive, LoggerConsoleLive))
)
);
🔶 Pull request comments
import {
RepoArgs,
OctokitLayer,
OctokitLayerLive,
LoggerConsoleLive,
} from 'effect-octokit-layer';
const reactRepo: RepoArgs = {
owner: 'facebook',
name: 'react',
};
const pull = repo.pull(39);
const review = pull.review(2593339077);
const [details, comments, reviews, createdReview, deletedReview] =
await Effect.runPromise(
pipe(
Effect.all([
// Create a comment in review #2593339077 on pull request #39
review.comments.create({
path: './src',
body: 'cool',
commitId: 'ff',
}),
// Get review #2593339077 comments
review.comments.get(),
// Delete comment #1 in review #2593339077
review.comments.delete(1),
])
)
);
🔶 Parallelism and resilience
🧿 Concurrency
Default:
10
You can specify the concurrency
parameter on calls doing several requests in parallel (paginated data). For example:
// Will fetch the first page and then 100 pages concurrently
OctokitLayer.repo({
owner: 'facebook',
name: 'react',
}).pulls(100);
Note that github api enforces api rate limits. Fetching too many results concurrently will cause an api rate limit. In that case, a warning will be displayed and the call will be attempted again after the time window provided by github api (typically 60 seconds).