GithubHelp home page GithubHelp logo

ivangabriele / postgrester Goto Github PK

View Code? Open in Web Editor NEW
50.0 4.0 7.0 1.63 MB

Isomorphic PostgREST API Client for Javascript and Typescript.

License: Apache License 2.0

JavaScript 28.41% TypeScript 71.59%
postgrest api api-client javascript typescript isomorphic

postgrester's Introduction

postgrester

⚠️ THIS PACKAGE IS DEPRECATED AND NO LONGER MAINTAINED, YOU CAN USE @supabase/postgrest-js AS A REPLACEMENT.


License NPM Package Build Status Code Coverage

Isomorphic PostgREST API Client for Javascript and Typescript.

Supported PostgREST versions:

  • v9.0.0
  • v8.0.0

Gettting Started

npm i postgrester

Example

import { create } from "postgrester";

const postgrestClient = create({
  axiosConfig: { baseURL: "https://api.example.com" }
});

(async () => {
  const { data, pagesLength } = await postgrestClient
    .select("*")
    .select("author(first_name,last_name)")
    .is("is_published", true)
    .not.is("isbn", null)
    .eq("publication_year", 1970)
    .in("language_code", ["en-UK", "en-US"])
    .ilike("title", "island")
    .like("author.last_name", "Hemingway")
    .orderBy("publication_year", true) // `true` = DESC
    .orderBy("title")
    .page(3, 25) // 4th page with 25 items per page
    .get("/books", true); // `true` = require the total `pagesLength` value to be calculated
})();

API

Options

When creating the instance via create([options]):

Property Type Default Description
axiosConfig AxiosRequestConfig {} Axios config called with axios.create().
axiosInstance AxiosInstance null Axios custom instance.
baseUri string "" API URL. Deprecated

⚠️ If you provide an axios instance via the axiosInstance property, it's useless to set axiosConfig since it would be overridden by your instance.

⚠️ baseUri takes precedence over axiosConfig.baseURL. To avoid any confusion, baseUri will be deprecated in the next minor version release and should be removed in the next major one.

Vertical Filtering (columns) Methods

select()

Name Type Default Examples
selector string required "*", "author", "category(id,label)"

You can also rename them by inserting a colon: original_column_name:new_column_name.

Hoizontal Filtering (rows) Methods

is()

Name Type Default Examples
column string required "author", "category.label"
value boolean | null required

eq()

Name Type Default Examples
column string required "author", "category.label"
value boolean | number | null | string required "Leo Tolstoy"
withQuotes boolean false

Note: boolean and null values will be converted into an is().

neq()

Name Type Default Examples
column string required "author", "category.label"
value boolean | number | null | string required "Leo Tolstoy"
withQuotes boolean false

Note: boolean and null values will be converted into a negated is().

gt()

Name Type Default Examples
column string required "quantity", "category.updated_at"
value number | string required
isInclusive boolean false

gte()

Name Type Default Examples
column string required "quantity", "category.updated_at"
value number | string required

Note: This method is an alias for gt() with <isInclusive> set to true.

lt()

Name Type Default Examples
column string required "quantity", "category.updated_at"
value number | string required
isInclusive boolean false

lte()

Name Type Default Examples
column string required "quantity", "category.updated_at"
value number | string required

Note: This method is an alias for lt() with <isInclusive> set to true.

in()

Name Type Default Examples
column string required "author", "category.label"
value Array<number | string> required ["Leo Tolstoy", "Fyodor Dostoevsky"]
withQuotes boolean false

like()

Name Type Default Examples
column string required "author", "category.label"
value string required "Tolstoy"

ilike()

Name Type Default Examples
column string required "author", "category.label"
value string required "tolstoy"

not

This getter ONLY negates the FIRST following filtering method.

For example, postgrestClient.not.is("category_id", null).ilike("author", "dostoevsky") will negate the is() filter but not the ilike() one.

and

This getter condition ALL the following filtering methods to be conjuncted as "ands".

For example, postgrestClient.and.is("category_id", null).ilike("author", "dostoevsky") will intersect both is() and ilike() filters.

or

This getter condition ALL the following filtering methods to be conjuncted as "ors".

For example, postgrestClient.and.is("category_id", null).ilike("author", "dostoevsky") will unite both is() and ilike() filters.

Ordering Methods

orderBy()

Name Type Default Examples
column string required "author", "category.label"
isDesc boolean false

Pagination Methods

page()

Name Type Default Examples
pageIndex number required 0, 123
limit number 10

Request Methods

All request methods are asynchronous promises.

get()

Name Type Default Examples
path string required "/books"
withPagesLength boolean false

Return value:

Promise<{
  data: any;
  pagesLength: number;
  totalLength: number;
}>

⚠️ Important
Both pagesLength and totalLength will equal -1 if <withPagesLength> parameter is false or if the length couldn't be resolved.

post() / Insert

Name Type Default Examples
path string required "/books"
data object required
options { return?: 'headers-only' | 'representation' }

Return value:

Promise<void>

or (with { return: "representation" }):

Promise<{
  data: T
}>

post() / Upsert

⚠️ Important
If data is an array, it will be considered as an upsert.
In this case, if you don't specify otherwise in options, merge-duplicates resolution will be used by default.

Name Type Default Examples
path string required "/books"
data object[] required
options { onConflict?: string, resolution?: "ignore-duplicates" | "merge-duplicates", return?: 'headers-only' | 'representation' } { resolution: "merge-duplicates" }

Return value:

Promise<void>

or (with { return: "representation" }):

Promise<{
  data: T[]
}>

patch()

Name Type Default Examples
path string required "/books"
data object required

Return value:

Promise<void>

put()

Name Type Default Examples
path string required "/books"
data object required

Return value:

Promise<void>

delete()

Name Type Default Examples
path string required "/books"
options { return?: 'headers-only' | 'representation' }

Return value:

Promise<void>

or (with { return: "representation" }):

Promise<{
  data: T[]
}>

Contribute

Please check our contributing documentation.

License

This package and its sources are distributed under Apache 2.0.


postgrester's People

Contributors

dependabot-preview[bot] avatar dependabot[bot] avatar douglasduteil avatar ivangabriele avatar renovate-bot avatar renovate[bot] avatar semantic-release-bot avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

postgrester's Issues

Support Prefer: return=representation

🚀 Support Prefer: return=representation

When inserting, updating, or deleting records via PostgREST, you can send the Prefer: return=representation header, which will return the object that was written. This is especially helpful when you create new records and need the id that was generated by the database. Currently, the promise returned by post, patch and delete is Promise<void>, but having a return such as Promise<{data: any}> would be great if the representation (or any of the specific columns specified via the query select=id syntax) would be available.

You can see more about the Prefer options here: http://postgrest.org/en/v7.0.0/api.html#insertions-updates

Motivation

Right now if I create a record, I am unable to get database generated columns, such as the id.

Example

(async () => {
  const {data} = await postgrestClient
    .select(["id"])
    .post("/tasks", {"name": "get this working"}, {return: "representation"});
  
  console.log(data.id);
})();

Pitch

This would make it possible to get return values from PostgREST. Also, when you want to add support for stored procedures via the /rpc path, it would be easy, as you can use the same capabilities to return values from the stored procedure call.

client.post Error: Request failed with status code 400

🐛 Bug Report

const { data } = await client.post("/m_works", { "col1": "value1", "col2": "value2" }, {return: "representation"});

Error: Request failed with status code 400
    at createError (D:\powerx-mes-app-backend\node_modules\postgrester\node_modules\axios\lib\core\createError.js:16:15)
    at settle (D:\powerx-mes-app-backend\node_modules\postgrester\node_modules\axios\lib\core\settle.js:17:12)
    at IncomingMessage.handleStreamEnd (D:\powerx-mes-app-backend\node_modules\postgrester\node_modules\axios\lib\adapters\http.js:312:11)
    at IncomingMessage.emit (events.js:412:35)
    at endReadableNT (internal/streams/readable.js:1334:12)
    at processTicksAndRejections (internal/process/task_queues.js:82:21)


Like request results in quoted param, not compatible

🐛 Bug Report

I use the like function to allow query for search results. The like value is surrounded by quotes (as in the source code explicitly defined). The value being surrounded by quotes seems not compatible.

Example:

    const { data } = await postgrestClient
      .select('*')
      .eq('type', type)
      .like('name', 'ren')
      .get('/zones');

Results in query param: "like.\"*ren*\"".
This returns no results. But when I custom query the api with GET /zones?limit=100&type=eq.municipality&name=ilike.*ren* this does work.

envinfo

[email protected]
PostgREST 6.0.2

System:

  • OS: macOS 10.15.3
  • CPU: (12) x64 Intel(R) Core(TM) i7-8750H CPU @ 2.20GHz
  • Memory: 363.68 MB / 16.00 GB
  • Shell: 5.7.1 - /bin/zsh

Binaries:

  • Node: 12.14.1 - ~/.nvm/versions/node/v12.14.1/bin/node
  • Yarn: 1.15.2 - /usr/local/bin/yarn
  • npm: 6.13.4 - ~/.nvm/versions/node/v12.14.1/bin/npm

Dependency Dashboard

This issue lists Renovate updates and detected dependencies. Read the Dependency Dashboard docs to learn more.

Awaiting Schedule

These updates are awaiting their schedule. Click on a checkbox to get an update now.

  • build(dev-deps): update dependency @ivangabriele/eslint-config-typescript-base to v6
  • build(dev-deps): update dependency @rollup/plugin-commonjs to v24
  • build(dev-deps): update dependency @rollup/plugin-node-resolve to v15
  • build(dev-deps): update dependency @rollup/plugin-typescript to v11
  • build(dev-deps): update dependency eslint-plugin-jest to v27
  • build(dev-deps): update dependency rollup to v3
  • build(dev-deps): update dependency typescript to v5
  • chore(deps): update postgres docker tag to v15
  • fix(deps): update dependency axios to v1

Open

These updates have all been created already. Click a checkbox below to force a retry/rebase of any.

Detected dependencies

docker-compose
docker-compose.yml
  • postgres 14
github-actions
.github/workflows/check.yml
  • actions/checkout v3
  • actions/setup-node v3
  • actions/checkout v3
  • actions/setup-node v3
  • actions/checkout v3
  • actions/setup-node v3
.github/workflows/release.yml
  • actions/checkout v3
  • actions/setup-node v3
npm
package.json
  • axios 0.27.2
  • @ivangabriele/eslint-config-typescript-base 2.1.4
  • @ivangabriele/prettier-config 3.0.2
  • @ivangabriele/semantic-release-config-base 2.0.2
  • @rollup/plugin-commonjs 22.0.0
  • @rollup/plugin-node-resolve 13.3.0
  • @rollup/plugin-typescript 8.3.2
  • @types/jest 27.5.1
  • bhala 2.1.0
  • codecov 3.8.3
  • cross-env 7.0.3
  • eslint-plugin-jest 26.2.2
  • husky 8.0.1
  • jest 27.5.1
  • knex 2.0.0
  • pg 8.7.3
  • rollup 2.74.1
  • shelljs 0.8.5
  • ts-jest 27.1.5
  • typescript 4.6.4
  • node >= 10

  • Check this box to trigger a request for Renovate to run again on this repository

Consider supporting JSON datatypes

🚀 Feature Proposal

Postgrest supports selecting and filtering on json or jsonb columns: https://postgrest.org/en/stable/api.html#json-columns
It would be great if we could add this to the client.

Motivation

I want to request some specific data from a JSON column or filter by entries that have some data in a JSON column.

Example

client.selectJSON("json_data.phones[0].number")

client.lt("json_data.countries.population", 1000000)

Pitch

This would make it more convenient than having to write custom queries just for these columns.

Thanks for this great library!

I have a related question: If I wanted to use postgrester to generate a postgrest query URL and then add on to it myself (e.g. to filter JSON data), and either make the request myself/pass it back into Postgrester, what are the best functions to use?

Modifing axios request config

🚀 Feature Proposal

It would great to be able to modify the axios request config

Motivation

For me, personally, there are multiple motivations, they are:

  • cancel requests, which requires providing the cancelToken attribute.
  • uploadProgress, which requires providing the onUploadProgress attribute.
  • custom headers, which requires providing the headers attribute. This might be a tougher one to implement as

Example

I imagine this would be implemented in a similar way to how axios implements this.
That is providing a final attribute to each request method that sets these options.

import postgrester from "postgrester";

 const CancelToken = axios.CancelToken;
 const source = CancelToken.source();

const postgrestClient = postgrester.create({
  axiosConfig: { baseURL: "https://api.example.com" }
});



(async () => {
  const { data, pagesLength } = await postgrestClient
    .select("*")
    .select("author(first_name,last_name)")
    .is("is_published", true)
    .not.is("isbn", null)
    .eq("publication_year", 1970)
    .in("language_code", ["en-UK", "en-US"])
    .ilike("title", "island")
    .like("author.last_name", "Hemingway")
    .orderBy("publication_year", true) // `true` = DESC
    .orderBy("title")
    .page(3, 25) // 4th page with 25 items per page
    .get("/books", true, {
       cancelToken: source.token, 
       headers: { 'Authorization' : 'Bearer ' + localStorage.getItem('jwtToken')}
})();

Pitch

I believe this belongs in Postgrester as postgrester provides a way to manage requests to a postgrest instance and for a request, there is a need to


Aside: Thanks, this looks like an incredibly well-maintained project.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.