atom-nuxt
v1.0.105
Published
My new Nuxt module
Downloads
1,688
Readme
Atom Nuxt
Features
- Crud operations
- Components for pagination and filtering
- Baz
Quick Setup
Install the module to your Nuxt application with one command:
npx nuxi module add atom-nuxt
That's it! You can now use My Module in your Nuxt app ✨
# Install dependencies
npm install
# Generate type stubs
npm run dev:prepare
# Develop with the playground
npm run dev
# Build the playground
npm run dev:build
# Run ESLint
npm run lint
# Run Vitest
npm run test
npm run test:watch
# Release new version
npm run release
CRUD API and Pagination Loader
This repository provides a composable for managing CRUD operations and a Vue component for rendering a paginated list of items with filtering and actions.
Table of Contents
useCrudApi Composable
The useCrudApi
composable provides a set of functions and reactive state management for performing CRUD operations against a specified API endpoint. It integrates authentication handling, pagination, filtering, and error management.
Usage
import { useCrudApi } from 'path/to/useCrudApi';
const { getItems, createItem, updateItem, deleteItem, items, currentPage } = useCrudApi('your/api/path');
Parameters
- path:
string
- The API endpoint path. - watchPage:
boolean
(optional, default:true
) - Whether to watch the current page for changes. - transformItem:
Function
(optional) - A function to transform a single item. - transformItems:
Function
(optional) - A function to transform multiple items.
Returns
- items:
Ref<Array>
- The list of items fetched from the API. - currentPage:
Ref<number>
- The current page number. - totalPages:
Ref<number>
- The total number of pages available. - totalItems:
Ref<number>
- The total number of items available. - perPage:
Ref<number>
- The number of items per page. - filters:
Ref<Record<string, any>>[]
- The active filters. - item:
Ref<any>
- The currently selected item. - count:
Ref<number>
- The count of items. - listErrors:
Ref<Record<string, any>>
- Errors encountered during list fetches. - formErrors:
Ref<Record<string, any>>
- Errors encountered during form submissions. - itemErrors:
Ref<Record<string, any>>
- Errors encountered when fetching or updating a single item. - countErrors:
Ref<Record<string, any>>
- Errors encountered when fetching counts. - exportErrors:
Ref<Record<string, any>>
- Errors encountered during export operations. - hasFormErrors:
Ref<boolean>
- Indicates if there are form errors. - hasItemErrors:
Ref<boolean>
- Indicates if there are item errors. - hasCountErrors:
Ref<boolean>
- Indicates if there are count errors. - hasExportErrors:
Ref<boolean>
- Indicates if there are export errors. - listPending:
Ref<boolean>
- Indicates if a list fetch is pending. - formPending:
Ref<boolean>
- Indicates if a form operation is pending. - itemPending:
Ref<boolean>
- Indicates if fetching or updating an item is pending. - countPending:
Ref<boolean>
- Indicates if a count fetch is pending. - exportPending:
Ref<boolean>
- Indicates if an export operation is pending. - getItems:
Function
- Fetches the items from the API. - createItem:
Function
- Creates a new item in the API. - updateItem:
Function
- Updates an existing item in the API. - deleteItem:
Function
- Deletes an item from the API.
CrudPaginatedLoader Component
The CrudPaginatedLoader
component provides a UI for displaying a paginated list of items, along with options for filtering, creating, updating, and deleting items.
Usage
<script setup>
</script>
<template>
<crud-paginated-loader
path="your/api/path"
:custom-filters="{}"
create-title="Create Item"
update-title="Update Item"
delete-title="Delete Item"
:per-page="10"
:listeners="['onItemCreated']" <!-- List of events to listen for from useListenerService and reload results when the happen -->
:await="false" <!-- Set to true to wait for the fetchItems function to resolve before rendering -->
>
<!-- Your custom slots here -->
<template #before="{
items,
listPending,
createForm,
updateForm,
deleteForm,
formPending,
exportAction,
exportPending,
exportErrors
}">
<!-- Your custom content here -->
<v-btn @click="createForm">Open create form</v-btn>
<v-btn :loading="exportPending" @click="exportItems">Export filtered items</v-btn>
</template>
<template #default="{
items, // The list of items in current page
pending, // If the list is loading
updateForm, // Action to show the update form
deleteForm, // Action to show the delete form
formPending // If the form is loading
}">
<!-- Your item list here -->
<v-simple-table>
<template #default="{ items }">
<tr v-for="item in items" :key="item.id">
<td>{{ item.name }}</td>
<td>{{ item.email }}</td>
<td>
<v-btn @click="updateForm(item.id)">Edit</v-btn>
<v-btn @click="deleteForm(item.id)">Delete</v-btn>
</td>
</tr>
</template>
</v-simple-table>
</template>
<template #form="{
action, // The action to perform (create, update, delete)
item, // The item object to update prior to form submission
errors // The errors with any form submission
}">
<!-- Your form layout here typically in it's own component for neatness and reusability -->
<v-text-field
v-model="item.name"
label="Name"
:error="errors.name"
:error-messages="errors.name"
/>
<v-text-field
v-model="item.email"
label="Email"
:error="errors.email"
:error-messages="errors.email"
/>
</template>
</crud-paginated-loader>
</template>
Props
- fetchItems:
Function
- A function to fetch the items.
useListenerService
The useListenerService
is a utility service for managing event listeners in a JavaScript application. It allows you to add, remove, and notify listeners based on specific events.
Overview
This service is useful for applications that need to respond to various events without tightly coupling components. It provides a way to manage listeners dynamically, ensuring that they can be added or removed as needed.
Types
Listener
type Listener = {
id: string; // Unique identifier for the listener
event: string; // Name of the event to listen for
callback: Function; // Function to call when the event occurs
};
Functions
useListenerService
This function initializes and returns the listener service, providing methods to manage listeners.
Returns
An object containing the following methods:
removeLocalListeners:
- Removes all listeners that were added during the current session.
removeLocalListenersWithEvent(event: string):
- Removes all local listeners associated with a specific event.
- Parameters:
event
: The name of the event whose listeners should be removed.
addListener(event: string, callback: Function):
- Adds a new listener for the specified event.
- Parameters:
event
: The name of the event to listen for.callback
: The function to call when the event is triggered.
- Returns: The unique identifier (ID) of the added listener.
removeListener(id: string):
- Removes a listener by its unique identifier.
- Parameters:
id
: The unique identifier of the listener to be removed.
notify(key: string, data: any):
- Triggers all callbacks for listeners associated with the specified event.
- Parameters:
key
: The name of the event to notify.data
: The data to pass to the callback functions.
Example Usage
const listenerService = useListenerService();
// Adding a listener
const listenerId = listenerService.addListener('myEvent', (data) => {
console.log('Event received:', data);
});
// Notifying listeners
listenerService.notify('myEvent', { key: 'value' });
// Removing a specific listener
listenerService.removeListener(listenerId);
// Removing all local listeners
listenerService.removeLocalListeners();
useCrudConverters
This composable provides a variety of utility functions for handling CRUD operations, formatting dates, converting files, and manipulating query strings in a Nuxt application.
Usage
Import useCrudConverters
where needed in your Nuxt components or composables.
import { useCrudConverters } from '~/path/to/composables';
Available Methods
localDateForDb(date: Date): string
Converts a local Date
object to a UTC ISO string formatted for database storage.
cloneDeep(obj: any): any
Performs a deep clone of the provided object.
flattenQuery(obj: Record<string, any>, prefix = ''): Record<string, any>
Flattens nested objects into a single-level query string-compatible format.
parseQuery(query: string): Record<string, any>
Parses a query string into a JavaScript object.
stringifyQuery(params: Record<string, any>, prefix: string = '', options: StringifyOptions): string
Converts an object to a query string with configurable formatting options.
params
: The object to stringify.prefix
: Prefix for the query string.options
: Optional settings such asarrayFormat
andskipNull
.
getFileType(file): number | null
Determines the file type based on its MIME type.
mimeTypeToMdiIcon(mimeType: string): string
Maps MIME types to Material Design Icons.
toBase64(file): Promise<string>
Converts a file to a Base64-encoded string.
convertAddress(item: Record<string, any>, separator = ', '): string
Concatenates address components into a formatted string.
formatRange(min: string, max: string, separator = ' - '): string
Formats a date range string for display, adjusting based on current date context.
formatDate(date: Date, format: Intl.DateTimeFormatOptions): string
Formats a Date
object according to provided formatting options.
formatStringDate(dateString: string, format: Intl.DateTimeFormatOptions): string
Formats a date string according to specified options.
parseDate(dateStr: string): Date
Parses a date string into a Date
object.
filtersToBase64String(filters: any): string
Encodes filter values into a Base64-encoded JSON string.
base64StringToObj(base64String: string): any | null
Decodes a Base64 string back into a JavaScript object.
extractFilterValues(filters: { key: string; value: any }[]): Record<string, any>
Extracts key-value pairs from an array of filter objects.
uploadFilenameToUrl(fileLocation: string, size: string): string
Constructs a URL for an uploaded file with specified size prefix (thumbnail
, medium
, large
).
uploadToUrl(upload: { fileLocation: string }, size: string): string
Similar to uploadFilenameToUrl
but takes an object with a fileLocation
property.
outputDateFromDb(dateStr: string, formatOut = 'dd/MM/yyyy'): string
Formats a UTC ISO date string from the database to the local timezone format.
inputDateForDb(dateStr: string, formatIn = 'dd/MM/yyyy'): string
Parses a date string in the local timezone and converts it to a UTC ISO date string for storage.
Example Usages
Flattening Query Parameters
const params = { user: { id: 1, name: "Alice" }, filters: { age: { min: 18, max: 30 }, isActive: true } }; const flatParams = flattenQuery(params); console.log(flatParams); // Output: { "user[id]": 1, "user[name]": "Alice", "filters[age][min]": 18, "filters[age][max]": 30, "filters[isActive]": true }
Encoding and Decoding Filters
const filters = { status: "active", roles: ["admin", "user"] }; const encodedFilters = filtersToBase64String(filters); const decodedFilters = base64StringToObj(encodedFilters); console.log(decodedFilters); // Output: { status: "active", roles: ["admin", "user"] }
Stringifying Query with Custom Options
const query = { name: "John", roles: ["admin", "user"], isActive: true }; const queryString = stringifyQuery(query, '', { arrayFormat: 'bracket' }); console.log(queryString); // Output: "name=John&roles[]=admin&roles[]=user&isActive=true"
Formatting Dates for Display and Storage
const dbDate = outputDateFromDb("2024-10-26T12:00:00Z", "dd MMM yyyy"); console.log(dbDate); // Output (localized): "26 Oct 2024" const isoDate = inputDateForDb("26/10/2024", "dd/MM/yyyy"); console.log(isoDate); // Output: "2024-10-26T00:00:00.000Z" (UTC format)
Converting a File to Base64
const fileInput = document.querySelector("input[type='file']"); fileInput.addEventListener('change', async (event) => { const file = event.target.files[0]; const base64String = await toBase64(file); console.log(base64String); });