Skip to main content

Documentation Index

Fetch the complete documentation index at: https://learn.social.plus/llms.txt

Use this file to discover all available pages before exploring further.

This guide covers advanced web/React-specific features, development workflows, and platform-specific considerations for social.plus UIKit.

Development Workflow

Open Source Development

For teams requiring complete customization control and transparency:
1

Clone Repository

Clone the open source UIKit repository:
git clone https://github.com/AmityCo/Amity-Social-Cloud-UIKit-Web-OpenSource.git
cd Amity-Social-Cloud-UIKit-Web-OpenSource
2

Install Dependencies

Install project dependencies:
pnpm install
3

Environment Setup

Create a .env file in the project root:
STORYBOOK_API_REGION=<API_REGION>
STORYBOOK_API_KEY=<API_KEY>
Replace <API_REGION> and <API_KEY> with your actual credentials.
4

Run Storybook (Optional)

View components in isolation using Storybook:
pnpm run storybook
Open http://localhost:6006 in your browser.

Linking to Your Project

1

Build the UIKit

Build the UIKit project:
pnpm run build
2

Link to Your Application

Navigate to your application directory and link the UIKit:
npm link file:<path-to-amity-ui-kit-repository> --save
3

Import and Use

Import and use the UIKit in your application:
import { AmityUiKitProvider, AmityUiKitSocial } from '@amityco/ui-kit-open-source';
import "@amityco/ui-kit-open-source/dist/index.css";

Advanced Configuration

Provider Configuration Options

PropertyTypeRequiredDescription
apiKeystringYesYour social.plus API key
userIdstringYesUnique identifier for the user
displayNamestringYesUser’s display name
apiRegionstringYesAPI region: “us”, “eu”, or “sg”
apiEndpointstringNoCustom API endpoint (optional)
configsConfigNoCustom theme and styling configuration
sessionHandlerobjectNoCustom session management
postRendererConfigobjectNoCustom post rendering options

Theme Configuration

Create a comprehensive configuration file amity-uikit.config.json:
{
  "global_theme": {
    "light_theme": {
      "primary_color": "#FFFFFF",
      "secondary_color": "#AB1234",
      "accent_color": "#1E88E5",
      "base_color": "#000000",
      "border_color": "#E0E0E0",
      "success_color": "#4CAF50",
      "warning_color": "#FF9800",
      "error_color": "#F44336"
    },
    "dark_theme": {
      "primary_color": "#1A1A1A",
      "secondary_color": "#AB1234",
      "accent_color": "#64B5F6",
      "base_color": "#FFFFFF",
      "border_color": "#424242",
      "success_color": "#66BB6A",
      "warning_color": "#FFB74D",
      "error_color": "#EF5350"
    }
  },
  "component_theme": {
    "social_feed": {
      "background_color": "#F5F5F5",
      "card_background": "#FFFFFF",
      "card_border_radius": "8px",
      "card_shadow": "0 2px 4px rgba(0,0,0,0.1)",
      "header_background": "#FFFFFF",
      "post_padding": "16px"
    },
    "chat": {
      "message_bubble_user": "#1E88E5",
      "message_bubble_other": "#E0E0E0",
      "message_text_user": "#FFFFFF",
      "message_text_other": "#000000",
      "input_background": "#FFFFFF",
      "input_border": "#E0E0E0"
    },
    "navigation": {
      "background_color": "#FFFFFF",
      "text_color": "#000000",
      "active_color": "#1E88E5",
      "border_color": "#E0E0E0"
    }
  },
  "typography": {
    "font_family": "Inter, -apple-system, BlinkMacSystemFont, sans-serif",
    "heading_weight": "600",
    "body_weight": "400",
    "small_weight": "400"
  }
}

Component-Specific Themes

"social_feed": {
  "background_color": "#F5F5F5",
  "card_background": "#FFFFFF",
  "card_border_radius": "12px",
  "card_shadow": "0 4px 6px rgba(0, 0, 0, 0.07)",
  "header_background": "#FFFFFF",
  "post_padding": "20px",
  "interaction_button_color": "#6B7280",
  "interaction_button_active": "#1E88E5",
  "like_animation": true,
  "show_engagement_bar": true
}
"chat": {
  "message_bubble_user": "#1E88E5",
  "message_bubble_other": "#F3F4F6",
  "message_text_user": "#FFFFFF",
  "message_text_other": "#1F2937",
  "input_background": "#FFFFFF",
  "input_border": "#D1D5DB",
  "input_border_radius": "8px",
  "message_border_radius": "16px",
  "timestamp_color": "#6B7280",
  "typing_indicator_color": "#9CA3AF"
}
"user_profile": {
  "header_background": "linear-gradient(135deg, #667eea 0%, #764ba2 100%)",
  "header_text_color": "#FFFFFF",
  "stats_background": "#F9FAFB",
  "stats_text_color": "#374151",
  "bio_text_color": "#6B7280",
  "follow_button_background": "#1E88E5",
  "follow_button_text": "#FFFFFF"
}

Component Usage Examples

Advanced Social Feed

import { AmityUiKitSocial, AmityPostComposer } from '@amityco/ui-kit-open-source';

function AdvancedSocialFeed() {
  const feedConfig = {
    enablePostComposer: true,
    showEngagementBar: true,
    enableInfiniteScroll: true,
    postsPerPage: 10,
    enableLiveUpdates: true
  };

  return (
    <div className="social-feed-container">
      <AmityPostComposer 
        placeholder="What's on your mind?" 
        enableImageUpload={true}
        enableVideoUpload={true}
        enablePollCreation={true}
      />
      <AmityUiKitSocial 
        config={feedConfig}
        onPostClick={(post) => console.log('Post clicked:', post)}
        onUserClick={(user) => console.log('User clicked:', user)}
      />
    </div>
  );
}

Chat with Custom Features

import { AmityUiKitChat, AmityChatRoom } from '@amityco/ui-kit-open-source';

function AdvancedChatInterface({ channelId }) {
  const chatConfig = {
    enableFileSharing: true,
    enableVoiceMessage: true,
    enableMessageReactions: true,
    enableTypingIndicator: true,
    messageHistoryLimit: 50
  };

  return (
    <div className="chat-container">
      <AmityChatRoom 
        channelId={channelId}
        config={chatConfig}
        onMessageSent={(message) => console.log('Message sent:', message)}
        onFileUploaded={(file) => console.log('File uploaded:', file)}
      />
    </div>
  );
}

Custom User Profile

import { AmityUiKitProfile, AmityUserInfo } from '@amityco/ui-kit-open-source';

function CustomUserProfile({ userId }) {
  const profileConfig = {
    showFollowButton: true,
    showMessageButton: true,
    showPostsTab: true,
    showFollowersTab: true,
    enableProfileEdit: true
  };

  return (
    <div className="profile-container">
      <AmityUserInfo userId={userId} />
      <AmityUiKitProfile 
        userId={userId}
        config={profileConfig}
        onFollow={(user) => console.log('Following:', user)}
        onMessage={(user) => console.log('Messaging:', user)}
      />
    </div>
  );
}

Performance Optimization

Bundle Optimization

1

Tree Shaking

Import only the components you need:
// Instead of importing everything
import { AmityUiKitProvider } from '@amityco/ui-kit-open-source';

// Import specific components
import { AmityUiKitSocial } from '@amityco/ui-kit-open-source/social';
import { AmityUiKitChat } from '@amityco/ui-kit-open-source/chat';
2

Code Splitting

Use dynamic imports for route-based code splitting:
import { lazy, Suspense } from 'react';

const SocialFeed = lazy(() => import('./components/SocialFeed'));
const ChatInterface = lazy(() => import('./components/ChatInterface'));

function App() {
  return (
    <Suspense fallback={<div>Loading...</div>}>
      <Routes>
        <Route path="/social" element={<SocialFeed />} />
        <Route path="/chat" element={<ChatInterface />} />
      </Routes>
    </Suspense>
  );
}
3

CSS Optimization

Load CSS conditionally based on used components:
// Load base styles
import "@amityco/ui-kit-open-source/dist/base.css";

// Load component-specific styles conditionally
if (useSocialFeatures) {
  import("@amityco/ui-kit-open-source/dist/social.css");
}

if (useChatFeatures) {
  import("@amityco/ui-kit-open-source/dist/chat.css");
}

Memory Management

import { useEffect, useRef } from 'react';
import { AmityUiKitProvider } from '@amityco/ui-kit-open-source';

function OptimizedApp() {
  const providerRef = useRef(null);

  useEffect(() => {
    // Cleanup on unmount
    return () => {
      if (providerRef.current) {
        providerRef.current.cleanup();
      }
    };
  }, []);

  return (
    <AmityUiKitProvider
      ref={providerRef}
      apiKey={apiKey}
      userId={userId}
      displayName={displayName}
      apiRegion={apiRegion}
      // Enable memory optimization
      enableMemoryOptimization={true}
      // Limit concurrent network requests
      maxConcurrentRequests={5}
      // Enable request caching
      enableRequestCaching={true}
    >
      {/* Your app content */}
    </AmityUiKitProvider>
  );
}

Testing

Unit Testing

import { render, screen } from '@testing-library/react';
import { AmityUiKitProvider, AmityUiKitSocial } from '@amityco/ui-kit-open-source';

// Mock the provider for testing
const MockAmityProvider = ({ children }) => (
  <AmityUiKitProvider
    apiKey="test-key"
    userId="test-user"
    displayName="Test User"
    apiRegion="us"
  >
    {children}
  </AmityUiKitProvider>
);

describe('Social Feed', () => {
  test('renders social feed component', () => {
    render(
      <MockAmityProvider>
        <AmityUiKitSocial />
      </MockAmityProvider>
    );
    
    expect(screen.getByTestId('social-feed')).toBeInTheDocument();
  });
});

Integration Testing

import { render, waitFor } from '@testing-library/react';
import userEvent from '@testing-library/user-event';

describe('Social Feed Integration', () => {
  test('posts new content', async () => {
    const user = userEvent.setup();
    
    render(
      <MockAmityProvider>
        <AmityUiKitSocial />
      </MockAmityProvider>
    );
    
    const postInput = screen.getByPlaceholderText('What\'s on your mind?');
    const postButton = screen.getByText('Post');
    
    await user.type(postInput, 'Test post content');
    await user.click(postButton);
    
    await waitFor(() => {
      expect(screen.getByText('Test post content')).toBeInTheDocument();
    });
  });
});

Troubleshooting

Common problems and solutions:
  1. Clear dependency cache:
    rm -rf node_modules package-lock.json
    npm install
    
  2. Package manager conflicts:
    # If using PNPM
    pnpm store prune
    
    # If using Yarn
    yarn cache clean
    
    # If using NPM
    npm cache clean --force
    
  3. TypeScript path mapping:
    // tsconfig.json
    {
      "compilerOptions": {
        "baseUrl": ".",
        "paths": {
          "@amityco/ui-kit-open-source": ["node_modules/@amityco/ui-kit-open-source"]
        }
      }
    }
    
CSS loading problems:
  1. Webpack configuration:
    module.exports = {
      module: {
        rules: [
          {
            test: /\.css$/,
            use: ['style-loader', 'css-loader']
          }
        ]
      }
    };
    
  2. Vite configuration:
    import { defineConfig } from 'vite';
    
    export default defineConfig({
      css: {
        postcss: './postcss.config.js'
      }
    });
    
  3. Next.js configuration:
    // next.config.js
    module.exports = {
      transpilePackages: ['@amityco/ui-kit-open-source']
    };
    
Production build issues:
  1. Memory allocation:
    # Increase Node.js memory limit
    NODE_OPTIONS="--max-old-space-size=4096" npm run build
    
  2. Peer dependency conflicts:
    npm ls
    # Check for conflicting versions
    npm install --legacy-peer-deps
    
  3. Bundle analysis:
    # Analyze bundle size
    npm install --save-dev webpack-bundle-analyzer
    npx webpack-bundle-analyzer build/static/js/*.js
    
Authentication and connection issues:
  1. API credentials validation:
    // Verify credentials before initialization
    const validateCredentials = async () => {
      try {
        const response = await fetch(`https://api.${apiRegion}.amity.co/v3/sessions`, {
          method: 'POST',
          headers: {
            'Content-Type': 'application/json',
            'Authorization': `Bearer ${apiKey}`
          },
          body: JSON.stringify({ userId, displayName })
        });
        return response.ok;
      } catch (error) {
        console.error('Credential validation failed:', error);
        return false;
      }
    };
    
  2. Network debugging:
    <AmityUiKitProvider
      apiKey={apiKey}
      userId={userId}
      displayName={displayName}
      apiRegion={apiRegion}
      // Enable debug mode
      debug={true}
      // Custom error handler
      onError={(error) => console.error('UIKit Error:', error)}
    >
    
  3. CORS configuration:
    // If self-hosting, configure CORS
    app.use(cors({
      origin: ['https://yourdomain.com'],
      credentials: true
    }));
    

Next Steps

Component Styling

Deep dive into component-level customization

Theming Basics

Create and manage custom themes