Examples

User Management

Learn how to create, manage, and authenticate users in your multi-tenant application

User Management

This guide shows how to implement user management in your multi-tenant application using Nanostack's APIs.

Creating Users

Register a New User

curl -X POST \
  -H "Content-Type: application/json" \
  -d '{
    "email": "[email protected]",
    "password": "secure-password",
    "name": "John Doe",
    "organization_id": "org_123"
  }' \
  https://api.nanostack.dev/v1/auth/register

Response:

{
  "success": true,
  "data": {
    "user": {
      "id": "user_456",
      "email": "[email protected]",
      "name": "John Doe",
      "organization_id": "org_123",
      "role": "member",
      "created_at": "2024-01-01T00:00:00Z"
    },
    "token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
    "expires_at": "2024-01-02T00:00:00Z"
  }
}

Admin-Created Users

As an admin, you can create users directly:

curl -X POST \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer admin-jwt-token" \
  -d '{
    "email": "[email protected]",
    "name": "Jane Smith",
    "role": "admin",
    "organization_id": "org_123",
    "send_invite": true
  }' \
  https://api.nanostack.dev/v1/users

User Authentication

Login

curl -X POST \
  -H "Content-Type: application/json" \
  -d '{
    "email": "[email protected]",
    "password": "secure-password"
  }' \
  https://api.nanostack.dev/v1/auth/login

Using JWT Tokens

Include the JWT token in subsequent requests:

curl -H "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..." \
  https://api.nanostack.dev/v1/users/me

Refresh Tokens

curl -X POST \
  -H "Content-Type: application/json" \
  -d '{
    "refresh_token": "your-refresh-token"
  }' \
  https://api.nanostack.dev/v1/auth/refresh

User Roles and Permissions

Nanostack supports hierarchical roles:

Default Roles

  • Super Admin - Full system access
  • Tenant Admin - Tenant-level administration
  • Organization Admin - Organization management
  • Member - Basic user access
  • Guest - Limited read-only access

Custom Permissions

# Update user role
curl -X PUT \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer admin-jwt-token" \
  -d '{
    "role": "admin",
    "permissions": ["users:read", "users:write", "billing:read"]
  }' \
  https://api.nanostack.dev/v1/users/user_456

User Profile Management

Get Current User

curl -H "Authorization: Bearer jwt-token" \
  https://api.nanostack.dev/v1/users/me

Update Profile

curl -X PUT \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer jwt-token" \
  -d '{
    "name": "John Updated",
    "bio": "Software Developer",
    "avatar_url": "https://example.com/avatar.jpg"
  }' \
  https://api.nanostack.dev/v1/users/me

Change Password

curl -X PUT \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer jwt-token" \
  -d '{
    "current_password": "old-password",
    "new_password": "new-secure-password"
  }' \
  https://api.nanostack.dev/v1/users/me/password

Organization Members

List Organization Users

curl -H "Authorization: Bearer jwt-token" \
  https://api.nanostack.dev/v1/organizations/org_123/users

Invite User to Organization

curl -X POST \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer admin-jwt-token" \
  -d '{
    "email": "[email protected]",
    "role": "member",
    "message": "Welcome to our team!"
  }' \
  https://api.nanostack.dev/v1/organizations/org_123/invites

Remove User from Organization

curl -X DELETE \
  -H "Authorization: Bearer admin-jwt-token" \
  https://api.nanostack.dev/v1/organizations/org_123/users/user_456

Frontend Integration

React Example

import { useState, useEffect } from 'react'
import { NanostackClient } from '@nanostack/client'

const client = new NanostackClient({
  baseURL: 'https://api.nanostack.dev',
  token: localStorage.getItem('jwt_token')
})

function UserProfile() {
  const [user, setUser] = useState(null)
  const [loading, setLoading] = useState(true)

  useEffect(() => {
    const fetchUser = async () => {
      try {
        const response = await client.users.me()
        setUser(response.data)
      } catch (error) {
        console.error('Failed to fetch user:', error)
      } finally {
        setLoading(false)
      }
    }

    fetchUser()
  }, [])

  const updateProfile = async (data) => {
    try {
      await client.users.update('me', data)
      setUser({ ...user, ...data })
    } catch (error) {
      console.error('Failed to update profile:', error)
    }
  }

  if (loading) return <div>Loading...</div>

  return (
    <div>
      <h2>Welcome, {user.name}</h2>
      <p>Email: {user.email}</p>
      <p>Role: {user.role}</p>
      {/* Profile form here */}
    </div>
  )
}

Next.js API Route

// pages/api/users/[id].ts
import { NextApiRequest, NextApiResponse } from 'next'
import { NanostackClient } from '@nanostack/server'

const client = new NanostackClient({
  baseURL: process.env.NANOSTACK_API_URL,
  apiKey: process.env.NANOSTACK_API_KEY
})

export default async function handler(req: NextApiRequest, res: NextApiResponse) {
  const { id } = req.query

  try {
    switch (req.method) {
      case 'GET':
        const user = await client.users.get(id as string)
        return res.json(user)
      
      case 'PUT':
        const updated = await client.users.update(id as string, req.body)
        return res.json(updated)
      
      case 'DELETE':
        await client.users.delete(id as string)
        return res.status(204).end()
      
      default:
        return res.status(405).json({ error: 'Method not allowed' })
    }
  } catch (error) {
    console.error('API Error:', error)
    return res.status(500).json({ error: 'Internal server error' })
  }
}

Best Practices

Security

  • Always validate JWT tokens server-side
  • Use HTTPS in production
  • Implement rate limiting
  • Hash passwords with bcrypt
  • Use refresh tokens for long-lived sessions

Performance

  • Cache user data when appropriate
  • Implement pagination for user lists
  • Use database indexes for common queries
  • Consider Redis for session storage

User Experience

  • Provide clear error messages
  • Implement email verification
  • Support password reset flows
  • Use progressive enhancement

Common Patterns

User Registration Flow

  1. User submits registration form
  2. Validate email uniqueness
  3. Hash password securely
  4. Send verification email
  5. Create user account
  6. Return JWT token

User Invitation Flow

  1. Admin invites user by email
  2. System generates invitation token
  3. Send invitation email with link
  4. User clicks link to accept
  5. User sets password
  6. Account is activated

Troubleshooting

Common Issues

401 Unauthorized

  • Check JWT token validity
  • Verify token in Authorization header
  • Ensure user has proper permissions

422 Validation Error

  • Check required fields
  • Validate email format
  • Ensure password meets requirements

403 Forbidden

  • User lacks required permissions
  • Organization access denied
  • Resource doesn't belong to user's tenant

Next Steps