npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

frhooks

v2.2.4-6

Published

Hook React

Downloads

106

Readme

FRHooks React Js

Hook untuk membantu CRUD

or you can try frhooks V2 with a different name

ezhooks

Installation

Install with npm

  npm install frhooks

Install with Yarn

  yarn add frhooks
required:
  • yup
  • axios

Hooks

ApiRoute

apiRoute()
 .headers({...headers})
   - set header
 .params({...params})
   -set params url
 .get(resp => resp, {...config})
   -request GET
 .destroy(resp => resp, {...config})
   -request DELETE
 .data({...data})
   -set data (method POST | PUT)
 .sendJson(method, resp => resp, {...config})
   -mengirim data dalam bentuk json ("application/json")
 .sendUrlEncode(method, resp => resp, {...config})
   -mengirim data dalam bentuk query\ ("application/x-www-form-urlencoded")
 .sendFormData(method, resp => resp, {...config})
   -mengirim data dalam bentuk query ("multipart/form-data")
 .link()
   -generate url

Usage/Example

=> Buat url dalam 1 object
=> apiRoutes.js

const apiRoutes = {
  project: {
    index: "/project",
    detail: "/project/:id",
  },
  ...other,
};
export default apiRoutes;

=> Jika Menggunakan Typescript
=> Buat Typescript untuk url

declare namespace FRHooks {
  type Route = typeof import(".../apiRoutes").default
  type ApiRoute = {
    [P in keyof Route]: (
      path: keyof Route[P],
      arg?: Record<string, string>
    ) => Api;
  };
}

=> Daftar Provider
=> Buat instance dari Axios

import { HookProvider } from 'frhooks';
import axios from 'axios';
import apiRoutes from '../apiRoutes'

const api = axios.create({
  baseUrl: 'http://localhost:8000/api'
})

<HookProvider client={api} route={apiRoutes}>
  <App/>
</HookProvider>

=> Cara Menggunakan ApiRoute
=> Buat instance dari Axios
=> GET, POST, PUT, DELETE

import React FRHooks from 'react'
import {apiRoute} from 'frhooks'

function App(){
  const fetchData = async () => {
    data = await apiRoute().project('index').get()
  }

  const fetchDetail = async (id) => {
    data = await apiRoute().project('detail', {id}).get()
  }

  const postData = async () => {
    const data = await apiRoute()
          .project('index')
          .data({name:'Project A', description: ''})
          .sendJson('POST')
  }

  const destroyData = async () => {
    data = await apiRoute().project('detail', {id: 1}).destroy()
  }
}

useMutation

Manipulasi Form

Props

| Props | Fungsi | | -------------- | ----------------------------------------------------------------------------- | | defaultValue* | inialisasi nilai awal | | schema | schema validasi attribut menggunakan Yup | | format | memberikan format ketika inputan | | scenario | membagi validasi bedasarkan scenario |

Function you can use

| No | Object | Type | Fungsi | | --- | ------------------------------------ | -------- | ------------------------------------------------------------------------------------------ | | 1 | loading | boolean | Indikator saat request GET | | 2 | processing | boolean | Indiator saat POST, PUT, DESTROY | | 3 | data | T | Data | | 4 | errors | Object | Menampilkan error saat validasi | | 5 | isNewRecord | boolean | Inditator untuk data baru | | 6 | setData(value) | function | Fungsi untuk set data | | 7 | clearData(except:[]) | function | Membersihkan data tambahkan key jika ingin mengeluarkan data yang tidak ingin di bersihkan | | 8 | increment(value) | function | Fungsi untuk manaikan nilai | | 9 | decremet(value) | function | Fungsi untuk menurunkan nilai | | 10 | reformat(cb(value)) | function | Reformat data | | 11 | validate(key, scenario) | boolean | Mendapatkan validasi berdasarkan key | | 12 | fails(scenario) | function | Melakukan validasi manual | | 13 | setError({...error}) | function | Set manual error | | 14 | clearError() | function | Membersihkan Error validasi | | 15 | error(key) | function | Mendapatkan Error berdasarkan key | | 16 | message(key) | string | Mendapatkan pesan error berdasarkan key | | 17 | isValid() | function | Indikator untuk melihat validasi valid | | 18 | merge(values) | function | Menggabungkan data | | 19 | register(key, defaultValue, options) | function | Mendaftarkan Attribute input | | 20 | post | function | Aksi POST | | 21 | put | function | Aksi PUT | | 22 | destroy | function | Aksi DELETE | | 23 | get | function | Aksi GET | | 24 | cancel() | function | Membatalkan request axios | | 25 | addItem(Key, {value}, position) | function | Menambahkan value baru kedalam array | | 26 | setItem(value) | function | Mengubah nilai berdasarkan key | | 27 | getItem(Key, defaultValue) | function | Mendapatkan nilai berdasarkan key | | 28 | removeItem(key, index) | function | Menghapus value dari array berdasarkan index | | 29 | itemValid | boolean | | | 30 | setDispatch() | function | | | 31 | validateItem(key) | boolean | Mendapatkan validasi array berdasarkan index dan field | | 32 | attributes | array | Mendapatkan attribute atau field yand telah daftarkan | | 33 | incrementItem(value) | function | Fungsi untuk manaikan nilai | | 34 | decrementItem(value) | function | Fungsi untuk menurunkan nilai |

Usage/Example

// app.js
import React from 'react'
import {useMutation, useSelector} from 'frhooks'

const App = () => {
 const form = useMutation({
    defaultValue: {
      id: 0,
      title: "",
      body: "",
      items:[]
    },

    // Optional validasi
    schema: (yup: any) =>
      yup.object().shape({
        title: yup.string().required().label("Title"),
        body: yup.string().required().label("Description"),
        //Contoh Array
        items:yup.array().of(
            y.object().shape({
              label: y.string().required().label("Label"),
            })
          )
          .required()
      }),

    // Optional kondisi
    isNewRecord: (data) => data.id === 0,

    // Optional Scenario
    // Memecah field saat validasi berdasarkan scenatio
    scenario: {
      create: ["title"],
      update: ["title", "body"],
      step1: ["title"],
      step2: ["items"]
    },

    // Optional Format
    // Optional format saat input
    format: {
      title: (value) => value.trim(),
    },

    // Optional Tambah Key unik untuk mendaftarkan ke daftar CONTEXT
    key: 'key_context'
  });

// Contoh mengirim data POST | PUT
  const onSubmit = () => {
   // Note: ['/example/:id', {id}] gunakan ini jika butuh nilai
    form.post('/example', {
        // Optional default: post
        // Note: form.put(url, options) jika ingin menggunakan PUT
        method: "post",

        // Optional validasi, default false
        // Note: Pastikan schema telah ditambahkan
        validation: true,

        // Optional scenario, default: false
        // Note: Pastikan scenario telah ditambahkan
        scenario: "create",

        // Optional send post tanpa data, default: false
        useEmpty: false,

        // Optional send post tanpa data yang di filter
        except: [],

        // Optional send post hanya data yang di filter
        only: [],

        onBeforeSend: () => {
            console.log('action before send')
        },

        onSuccess: (data, jhqx) => {
            console.log('action on success', data)
        },
        onError:(e) => {
            console.log('error', e)
        },
        onAlways: () => {
            console.log('action on always')
        },
        options: {
          headers: {
             //default; application/json
             //Note: Ubah bagian ini jika ingin mengirim data menggunakan Form Data, useMutation akan mengubah secara otomatis object => form-data 'content-type': 'multipart/form-data',
             //Note: Ubah bagian ini jika ingin mengirim data menggunakan urlencode, useMutation akan mengubah secara otomatis object => query url encode 'content-type': "application/x-www-form-urlencoded",
              ...(other options axios config)
          }
        },
         ...(other options)
    })
  }

  // Contoh Delete
    const onDelete = () => {
        // Note: ['/example/:id', {id}] gunakan ini jika butuh nilai
        form.destroy('/example', {
            onSuccess: (data, jhqx) => {
                console.log('action on success', data)
             },
            ...(other options)
        })
    }

 // Contoh GET
    const get = () => {
        // Note: ['/example/:id', {id}] gunakan ini jika butuh nilai
        form.get('/example', {
            onSuccess: (data, jhqx) => {
                console.log('action on success', data)
              },
             ...(other options)
        })
    }

    const change={(e) => {
        form.setData({title: e.target.value})
    }

    //Membuat validasi saat blur
    cost blur={() => {
        form.validate('title')
    }

    //Contoh Manual Validasi
    const validation = async () => {
        //Normal
        const invalid = await form.fails();
        //Dengan scenario
        const invalid = await form.fails('step1')
        //Dengan Schema
        const invalid = await form.fails((yup) => yup.object().shape({...schema}))

        if(invalid) {
            console.log(form.errors)
        }
    }

    //Contoh Manual Validasi Array
    const validationArray = async () => {
        //Normal
        const invalid = await form.validateItem('items');
        if(invalid) {
            console.log(form.errors)
        }
    }

     const addNew = () => {
        form.addItem('items', {label: ''}, 'start' | 'end'| number of index)
    }

    //Note: Hapus Array
    const removeItem = (i) => () => {
        form.removeItem('items')
        //atau
        form.removeItem('items', i)
        //atau
        form.removeItem('items', (v) v.label === 'test')
    }

  render <div>
    {form.loading ? "Memuat Data..." : JSON.stringify(mutation.data)}

    <div>
      <input value={form.data.title} onChange={change} onBlur={blur}/>
      //Atau
      <input {...form.register('name',"",  {...options})}/>
      {form.error('title') ? <span>{form.message('title')}</span> : null}
    </div>

    <button onClick={validation} >validasi</button>
    <button disabled={!form.isValid()} onClick={onSubmit}>
        {form.processing ? "loading..." : "simpan"}
    </button>
  </div>
}

=> Jika Array

const App = () => {
    ...(form)
    return <div>
        <ul>
        {
            form.data.items.map((value, i) => (
                <li key={i}>
                <input
                value={form.getItem('items.0.label', '')}
                onChange={(e) => {
                    form.setItem( {['items.0.label']: e.target.value})
                }}
                onBlur={() => {
                    form.validateItem('items.0.label')
                }}
                />
                {form.error('items.0.label') ? <span>{form.message('items.0.label')}</span> : null}
                <button onClick={removeItem(i)}>- Remove Array</button>
                </li>
            )
        )}
    </ul>

    <button onClick={validationArray} >validasi array</button>
    <button onClick={addNew}> + Add New Array</button>
    </div>
}

=> Jika Nested Array dan Seterusnya

const App = () => {
    ...(form)
    return <div>
        <ul>
        {
            form.data.items.map((value, i) => value.items2.map((value2, i2) => (
               <li key={i}>
                <input
                value={form.getItem(`items.${i}.items2.${i2}.label`, '')}
                onChange={(e) => {
                    form.setItem( {[`items.${i}.items2.${i2}.label`]: e.target.value})
                }}
                onBlur={() => {
                    form.validateItem(`items.${i}.items2.${i2}.label`)
                }}
                />
                {form.error(`items.${i}.items2.${i2}.label`) ? <span>{form.message(`items.${i}.items2.${i2}.label`)}</span> : null}
                <button onClick={() => {
                  form.removeItem(`items.${i}.items2`, i2)
                }}>- Remove Array</button>
                </li>
            ))

            )
        }
    </ul>

    <button onClick={() => {
      form.validateItem(`items.${i}.items2`)
    }} >validasi array</button>
    <button onClick={() => {
      form.addItem(`items.${i}.items2`, {label: ''})
    }}> + Add New Array</button>
    </div>
}

useValidation

Menggunakan validasi schema (Yup)

Props

| Props | Fungsi | | -------- | ----------------------------------------------------------------------------- | | schema* | schema validasi attribut menggunakan Yup | | scenario | membagi validasi bedasarkan scenario | | value | Data |

Function you can use

| No | Props | Type | Fungsi | | --- | ---------------------------------------- | -------- | ------------------------------------- | | 1 | errors | object | Hasil validasi | | 2 | scenario | string | Mendapatkan scenario | | 3 | setData({}) | function | set data | | 4 | setError({}) | function | set error manual | | 5 | fails({scenario, value}) | function | Melakukan validasi | | 6 | validate(field, scenario) | boolean | Melakukan validasi per field | | 7 | clearError() | function | Menghapus error | | 8 | error(fields) | boolean | Mendapatkan indikasi error per field | | 9 | message(fields) | boolean | Mendapatkan pesan error per field | | 10 | valid | boolean | Mendapatkan indikasi error | | 11 | validateItem(key, attr, index, scenario) | boolean | Melakukan validasi item array | | 12 | errorItem(key, attr, index) | boolean | Mendapatkan indikasi error item array | | 13 | messageItem(key, attr, index) | string | Mendapatkan pesan error item array |

Usage/Example

// app.js
import React from 'react'
import {useValidation} from 'frhooks'
const App = () => {
 const form = useValidation({
    // Optional
    // value tambahkan value disini untuk validasi bersarkan perubahan data
    // form.setData(): jika value ditambahkan maka pada fungsi ini bisa untuk tidak digunakan
    value: data,
    schema: (yup: any) =>
      yup.object().shape({
        title: yup.string().required().label("Title"),
        body: yup.string().required().label("Description"),
        items: y
          .array()
          .of(
            y.object().shape({
              text: y.string().required().label("test"),
            })
          )
          .required(),
      }),

    // Optional Scenario
    // Memecah field saat validasi berdasarkan scenatio
    scenario: {
      create: ["title"],
      update: ["body"],
      //Experimental jika ingin memvalidasi hanya array saja
      //example: form.fails({scenario: "items"})
      validationItems: ["items"]
    },
  });

    const validation = async () => {
        //Normal
        const invalid = await form.fails();
        //Dengan scenario
        const invalid = await form.fails({scenario: "create"})
        //Dengan value
        const invalid = await form.fails({value: {...(new value)})
        if(invalid) {
            console.log(form.errors)
        }
    }
    return "Contoh sama dengan useMutation bukan Array"
}

=> Jika Array

    <ul>
        {array.map((v, i) => ( <div key={i}>
            <input onBlur={() => form.validateItem('items', 'text', i)} />
            {form.errorItem('items', 'text', i) ? <span>{form.messageItem('items', 'text', i)}</span> : null}
        </div>)}
    </ul>

useServerValidation

Menggunakan validasi asyncronus API

Props

| Props | Fungsi | | -------------------------------- | ------------------------------------------------------------- | ------------------------------- | | url | Alamat api yang dituju | | selector:(resp) => resp | Mendapatkan data error dengan normal response < 400 Http Code | | options: {[key]:(param, locale)} | Mengatur object error | | param: {type, path} | Mendapatkan object error | | field | object | Memberi pengaturan invidividual | | callback(err) | Mendpatkan balikan hasil error |

Function you can use

| No | Props | Type | Fungsi | | --- | ----------------------------------------- | -------- | ---------------------------------- | | 1 | processing | boolean | Mendapatkan indikasi proses | | 2 | errors | object | Mendapatkan error | | 3 | serve({url, key, only, method, data, cb}) | function | Melakukan validasi | | 4 | loading | boolen | Mendapatkan indikasi proses | | 5 | validate(key, data, options) | boolean | Melakukan validasi berdasarkan key |

Usage/Example

=> Contoh Error Response Api

//validation.json
error: [
    {path: "title", type: "required"},
    {path: "phoneNumber", type: 'exist'},
    {path: "body", type:"minLength", length: 8}
]

atau
// path dan type diubah menjadi field dan rule
error: [
  {field: "title", rule: "required"},
  ....
]

atau

error:{
  code: 5,
  name: "is exist"
}
// app.js
import React from 'react'
import {useServerValidation} from 'frhooks'
const App = () => {
 const {server, errors} = useServerValidation({
    url: "http://localhost/validation",
    // Mendapatkan error dari API
    selector: (resp) => resp.error,
    option: {
    //Note: Normal
    required: ({path}) => `${path} is required`,
    //Note: with locale
    required: ({path}, {r, t}) =>r("required", { path: t(path) }, "validation"),

    exist: ({path}) => `${path} already exist`,
    minLength:({path, length}) => `${path} minimum length is ${length}`,

    //Note: jika param diubah
    required: ({field}) => `${path} is required`,
    },

   // Optional
   // dapat diubah
    param:{
        path: "path",// default path,
        type: "type",// default type
    }
    field: {
        name: {
          url: "exmple.json",
          selector: (resp) => {
            // Balikan berupa string˝
            return resp.data.error.name
          }
        }
    },
    // Optional
    calback: (err) => {
        form.setError(err)
    }

  });

    const validation = async () => {
      const valid = await  serve({method: "post", ...(other optional options)})
      if(!valid){
          console.log(errors)
      }
    }

    //Note: Kombinasi dengan useMutation
    const onSubmit = () => {
        form.post('/example', {
        // Optional validasi, default false
        validation: true,
        serverValidation: {
            serve: serve,
            method: "post",
        },
         ...(other options)
    })
    }
    return <>{JSON.stringify(errors)}<>
}

useTable

Manipulasi Table

Props

| Props | Fungsi | | ------------------ | --------------------------------------- | | selector* | Mendapatkan data dari respon API | | total* | Mendapatkan jumlah data dari respon API | | disabledOnDidMount | Mematikan aksi saat didmount | | config | Konfigurasi AxiosRequestConfig | | sort | urutan | | pagination | paginasi | | key | Menambahkan data kedaftar CONTEXT |

Function you can use

| No | Object | Type | Fungsi | | --- | -------------------------------------- | ---------- | ---------------------------------------------------------------- | | 1 | loading | boolean | Indikator loading saat GET | | 2 | total | number | Menampilkan total | | 3 | data | T | Data | | 4 | orderBy | string | Menampilkan key urutan | | 5 | order | asd - desc | Menampilkan type urutan | | 6 | query(key, defaultValue) | function | Mendapatkan hasil set query | | 7 | setTotal(value) | function | Set total secara manual | | 8 | setQuery({value}) | function | Set query | | 9 | onOrder(key) | function | Sorting berdasarkan key | | 10 | clear() | function | Membersihkan query | | 11 | clearExcept([]) | function | Membersihkan query dengan parameter | | 12 | clearOnly([]) | function | Membersihkan query dengan parameter | | 13 | remove() | function | Membersihkan Error validasi | | 14 | reload() | function | Memuat ulang | | 15 | remove(key, resetPage) | function | Menghapus query berdasarkan key dan reset page = defaultPage | | 16 | add(value, "start" or "end" or number) | function | Menambahkan data baru kedalam list | | 17 | update(index or (v) => boolean, value) | function | Memperbaharui data list berdasarkan Index | | 18 | destroy(index or (v) => boolean) | function | Menghapus data darri list berdasarlkan Index | | 19 | isEmpty | boolean | Mendapatkan indikasi data kosong | | 20 | has(key) | boolean | Mendapatkan inidikasi dari key query | | 21 | setDispatch() | function | (key: 'list_test') diset untuk mendaftarkan data kedalam context | | 22 | pagination | Object | ... | | 23 | register() | function | ... |

Pagination Function you can use

| Object | Type | Fungsi | | ----------------- | -------- | ------------------------------------- | | page | number | Mendapatkan page | | from | number | Mendapatkan nomor urutan pertama | | to | number | Mendapatkan nomor urutan terakhir | | lastPage | number | Mendapatkan nomor page terakhir | | perPageOptions | number[] | Mendapatkan daftar size page tersedia | | perPage | number | Mendapatkan nilai size page | | setPage(value) | function | Set page manual | | setPerPage(value) | function | Set size page manual | | nextButton() | function | ... | | backButton() | function | ... | | firstButton() | function | ... | | lastButton() | function | ... | | onPerPageChange | function | fungsi untuk set nilai size page | | text | string | Mendapatkan summary data |

Usage/Examples

// list.json
//exmple API response
 {
  status: 200,
  data: [...],
  total: 10
 }
// app.js
import React from 'react'
import {useTable} from 'frhooks'
const App = () => {
  //Note: ["/examples/:path", {path: "test"}] bila ingin menambahkan  path
  const table = useTable("/examples", {
    // Mendapatkan data dari response API
    selector: (resp) => resp.data,
    // Mendapatkan nilai total dari response API
    total: (resp) => resp.total,
    // Optional
    // Note: Cara merubah params sorting
    // Example: localhost/example?order=asc&orderby=id
    sort: {
      params: {
        order: "order",
        orderBy: "orderBy",
      },
      order: "desc", // Note: default order, default: desc
      orderBy: "id", // Note: default orderBy, default: id
    },
    // Optional
    // Note: Melakukan custome terhadap pagination
    pagination: {
      //Example: localhost/example?page=1&perPage=10
      params: {
        page: "page",
        perPage: "perPage",
      },
      startPage: 1,// default page, default: 1 or 0
      perPage: 10,// default perPage, default: 10,
      perPageOptions: [5, 10, 15, 25],
      // formula mendapatkan nilai from
      from: (total, page, size, df) => page - 1 + (df === 0 ? 1 : 0)) * size +
      (total === 0 ? 0 : df === 0 ? 1 : df),
       // formula mendapatkan nilai to
      to: (total, page, size, df) =>  Math.min(total, (page + (df === 0 ? 1 : 0)) * size),
      //Mendapatkan nilai page terakhir
      lastPage: (total, size) => Math.max(0, Math.ceil(total / size)), // formula
      disableFirst: (total, page, df) => total !== 0 && page === df,
      disableLast: (total, page, lp) => total !== 0 && page === lp,
    },
    // Optional mendaftarkan hasil ke CONTEXT
    key: 'key_context',
    //tambahkan true jika tidak ingin menjalan saat load page, default: false
    disabledOnDidMount: false
  })

  render <div>
      <div>
      <input type="text" value={table.query('title', '')} onChange={e => table.setQuery({title: e.target.value})} />
      //atau
      <input type="text" {...table.register("title", "")} />

          {table.pagination.text}
          <button {...table.pagination.firstButton()}>prev</button>
          <button {...table.pagination.backButton()}>prev</button>
          {table.pagination.page}
          <button {...table.pagination.nextButton()}>next</button>
          <button {...table.pagination.lastButton()}>next</button>

        <button onClick={() => table.onOrder("name")}>
            {table.order}-{table.orderBy}
        </button>
        <button onClick={table.clear}>Clear</button>
        <button onClick={table.reload}>Reload</button>
     </div>

      <table>
        <thead>
          <tr>
            <td>No</td>
            <td>Title</td>
          </tr>
        </thead>

        <tbody>
          {table.loading ? 'loading...' : null}

          {table.data.map((v: any, i) => (
            <tr key={i}>
              <td>{table.data.from + (i+1)}</td>
              <td>{v.title}</td>
            </tr>
          ))}
        </tbody>
      </table>
  </div>
}

useFetch

fetching data

Props

| Props | Fungsi | | ------------------ | --------------------------------- | | selector* | Mendapatkan data dari respon API | | defaultValue | Nilai default untuk data | | defaultParams | Nila default untuk query | | disabledOnDidMount | Mematikan aksi saat didmount | | config | Konfigurasi AxiosRequestConfig | | debounceTime | Nilau debounce saat setQuery | | deps | Depedencies | | getData(data) | Mendapatkan Data secara manual | | key | Menambahkan data kedaftar CONTEXT |

Function you can use

| No | Object | Type | Fungsi | | --- | -------------------------------------- | -------- | ------------------------------------------------------------------------- | | 1 | loading | boolean | Indikator loading saat GET | | 2 | total | number | Menampilkan total | | 3 | data | T | Data | | 4 | error | object | error query | | 5 | getQuery(key, defaultValue) | function | Mendapatkan hasil set query | | 6 | setQuery({value}) | function | Set query | | 7 | clear({except, only}) | function | Membersihkan query | | 14 | refresh() | function | Memuat ulang | | 16 | add(value, "start" or "end" or number) | function | Menambahkan data baru kedalam list (jika data dalam bentuk array) | | 17 | update(index or(v) => number, value) | function | Memperbaharui data list berdasarkan Index (jika data dalam bentuk array) | | 18 | destroy(index or (v) => number) | function | Menghapus data dari list berdasarkan Index (jika data dalam bentuk array) | | 19 | isEmpty | boolean | Mendapatkan indikasi data kosong | | 20 | has(key) | boolean | Mendapatkan indikasi dari key query | | 21 | setDispatch() | function | (key: 'list_test') diset untuk mendaftarkan data kedalam context |

Usage/Examples

// list.json
//exmple API response
 {
  status: 200,
  data: [...],
 }
 // atau
 {
  status: 200,
  data: {...},
 }
// app.js
import React from 'react'
import {useFetch} from 'frhooks'
const App = () => {
  //Note: ["/examples/:path", {path: "test"}] bila ingin menambahkan  path
  const project = useFetch("/examples", {
    // Mendapatkan data dari response API
    selector: (resp) => resp.data,
    // Mendapatkan nilai total dari respon API
    // Tentukan nilai awal jika array maka [] atau {}
    defaultValue: {},
    // Optional
    // Optional mendaftarkan hasil ke CONTEXT
    key: 'key_context',
    // Optional
    // Tambahkan true jika tidak ingin menjalan saat load page, default: false
    disabledOnDidMount: false ,
    // Optional
    // Jika ingin mendaptkan data secara manual
    getData: (value) => {
        console.log(value, 'data in here')
    }
    ...(other options)
  })

  render "Lebih kurang mirip useTable"
}

useDispatch

useSelector

context

Function you can use

| Object | Type | Fungsi | | -------------------- | -------- | ----------------------------------------- | | dispatch(key, value) | function | set data object atau list berdasarkan key | | clearMutation('key') | function | Bersihkan mutasi | | clearList('key') | function | Bersihkan list |

Usage/Examples

=> Jika menggunakan Typescript maka tambahkan ini

//index.d.ts override

declare namespace FRHooks {
  type DataContext = {
    user: {
      name: string;
    };
  };
}
// app.js
import React from 'react'
import {useDispatch, useSelector} from 'frhooks'

const App = () => {
    const {dispatch, clearMutation, clearList} = useDispatch()
    // atau
    const {dispatch} = useDispatch('key', {
     // Optional, default mutation
     // Note: Jika array maka ubah menjadi "list"
     type: 'mutation',
     // Optional hanya untuk bertipe list
     total: 0,
     defaultValue: {
       name: ''
     }
   })

  const result = useSelector(['key'])
  // atau modifikasi respon
  const result = useSelector(['key'], (data) => data)

 React.useEffect(() =>{
  dispatch('key', {name: 'test'})
 }, [])

  render <div>
  {JSON.stringify(result)}
  </div>
}

useLang

Multi Bahasa

Function you can use

| Object | Type | Fungsi | | --------- | -------- | --------------------------------- | | t() | function | Mendapatkan hasil terjemah bahasa | | r() | function | Memberi nilai berdasarkan param | | setLang() | function | Menentukan bahasa digunakan |

Usage/Examples

// en.json => pastikan nama file benar "${en}".json
// default json
// ini bisa digunakan untuk memodifikasi pesan validasi useMutation
 {
  "attribute": {
    "name": "Name"
  },
  "message": {
    "exampleMessage": "Hello Word",
    "exampleReplaceMessage": "Hello :name"
  },
  "validation": {
    "default": ":path is invalid",
    "required": ":path is a required field",
    "oneOf": ":path must be one of the follwing values: :values",
    "notOneOf": ":path must not be one of the following values: \":values\"",
    "defined": ":path must be defined",
    "stringLength": ":path must be exactly :length characters",
    "stringMin": ":path must be at least :min characters",
    "stringMax": ":path must be at most :max characters",
    "matches": ":path must match the following: \":regex\"",
    "email": ":path must be a valid email",
    "url": ":path must be a valid URL",
    "uuid": ":path must be a valid UUID",
    "trim": ":path must be a trimmed string",
    "lowercase": ":path must be a lowercase string",
    "uppercase": ":path must be a upper case string",
    "numberMin": ":path must be greater than or equal to :min",
    "numberMax": ":path must be less than or equal to :max",
    "lessThan": ":path must be less than :less",
    "moreThan": ":path must be greater than :more",
    "positive": ":path must be a positive number",
    "negative": ":path must be a negative number",
    "integer": ":path must be an integer",
    "dateMin": ":path field must be later than :min",
    "dateMax": ":path field must be at earlier than :max",
    "isValue": ":path field must be :value",
    "noUnknown": ":path field has unspecified keys: :unknown",
    "arrayMin": ":path field must have at least :min items",
    "arrayMax": ":path field must have less than or equal to :max items",
    "arrayLength": ":path must have :length} items"
  }
}
// id.json => pastikan nama file benar "${id}".json
// ini bisa digunakan untuk memodifikasi pesan validasi useMutation

 {
  "attribute": {
    "name": "Nama",
    "mandatory": "Wajib"
  },
  "message": {
    "exampleMessage": "Hallo Dunia",
    "exampleReplaceMessage": "Hallo :name"
  },
  "validation": {
    "default": ":path tidak valid",
    ...dll
  }
}

//tsconfig
{
  "compilerOptions": {
    "resolveJsonModule": true,
  }
}
// index.d.ts override*
declare namespace FRHooks {
  type AttributeKey =
    | keyof typeof import("../lang/en.json")["attribute"]
    | Array<keyof typeof import("../lang/en.json")["attribute"]>;

  type AttributeMessage =
    | keyof typeof import("../lang/en.json")["message"]
    | Array<keyof typeof import("../lang/en.json")["message"]>;

    type Lang = "en" | "id"
}
import { HookProvider } from 'frhooks';

const language = {
  lang: 'en',
  // folder berisikan file json, en.json, id.json, ...dll
  path: './lang/',
  fallback: 'en',
  // Optional tambah jika ingin memeliki nilai awal
  default: {...default},
  // Optional
  loading: true,
}

// index.js
<HookProvider language={language}>
  <App/>
</HookProvider>

// app.js
import React from 'react'
import {useLang} from 'frhooks'

const App = () => {
  const {t, r, setLang} = useLang()

 React.useEffect(() =>{
    setLang('id') // Set Bahasa
 }, [])

  render <div>
  <p>{t('name') || t(['name', 'mandatory'])}</p>
  <p>{r('exampleReplaceMessage', {name: 'BUDI'})}</p>
  </div>
}