nuxt-users 1.30.0 → 1.31.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +40 -0
- package/dist/module.json +1 -1
- package/dist/runtime/components/NUsersUserCard.vue +4 -1
- package/package.json +3 -2
- package/scripts/check-peer-dependencies.js +141 -0
- package/scripts/deploy-docs.sh +69 -0
- package/scripts/post-build.js +75 -0
- package/scripts/test-integration.sh +136 -0
- package/scripts/test-mysql.sh +54 -0
- package/scripts/test-postgresql.sh +93 -0
- package/scripts/test-sqlite.sh +23 -0
- package/scripts/test-unit.sh +15 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,6 +1,46 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
3
|
|
|
4
|
+
## v1.31.1
|
|
5
|
+
|
|
6
|
+
[compare changes](https://github.com/rrd108/nuxt-users/compare/v1.31.0...v1.31.1)
|
|
7
|
+
|
|
8
|
+
### 🩹 Fixes
|
|
9
|
+
|
|
10
|
+
- Includes scripts directory in the published package ([ceaa188](https://github.com/rrd108/nuxt-users/commit/ceaa188))
|
|
11
|
+
|
|
12
|
+
### 🏡 Chore
|
|
13
|
+
|
|
14
|
+
- **release:** V1.31.0 ([21907d3](https://github.com/rrd108/nuxt-users/commit/21907d3))
|
|
15
|
+
|
|
16
|
+
### ❤️ Contributors
|
|
17
|
+
|
|
18
|
+
- Rrd108 ([@rrd108](https://github.com/rrd108))
|
|
19
|
+
|
|
20
|
+
## v1.31.0
|
|
21
|
+
|
|
22
|
+
[compare changes](https://github.com/rrd108/nuxt-users/compare/v1.30.0...v1.31.0)
|
|
23
|
+
|
|
24
|
+
### 🚀 Enhancements
|
|
25
|
+
|
|
26
|
+
- Extends NUsersList with customizable user actions ([1ea4f61](https://github.com/rrd108/nuxt-users/commit/1ea4f61))
|
|
27
|
+
- Adds filtering functionality to user list ([c3d25a9](https://github.com/rrd108/nuxt-users/commit/c3d25a9))
|
|
28
|
+
|
|
29
|
+
### 🩹 Fixes
|
|
30
|
+
|
|
31
|
+
- Missing connector.options closes #96 ([#96](https://github.com/rrd108/nuxt-users/issues/96))
|
|
32
|
+
- Using user provided properties ([07dd6a2](https://github.com/rrd108/nuxt-users/commit/07dd6a2))
|
|
33
|
+
- Typo in file name ([d833e52](https://github.com/rrd108/nuxt-users/commit/d833e52))
|
|
34
|
+
- Includes scripts directory in the published package ([ceaa188](https://github.com/rrd108/nuxt-users/commit/ceaa188))
|
|
35
|
+
|
|
36
|
+
### 🏡 Chore
|
|
37
|
+
|
|
38
|
+
- **release:** V1.30.0 ([08d081c](https://github.com/rrd108/nuxt-users/commit/08d081c))
|
|
39
|
+
|
|
40
|
+
### ❤️ Contributors
|
|
41
|
+
|
|
42
|
+
- Rrd108 ([@rrd108](https://github.com/rrd108))
|
|
43
|
+
|
|
4
44
|
## v1.30.0
|
|
5
45
|
|
|
6
46
|
[compare changes](https://github.com/rrd108/nuxt-users/compare/v1.29.1...v1.30.0)
|
package/dist/module.json
CHANGED
|
@@ -17,12 +17,15 @@ onMounted(async () => {
|
|
|
17
17
|
authComposable.value = useAuthentication();
|
|
18
18
|
});
|
|
19
19
|
const canEdit = computed(() => {
|
|
20
|
+
console.log("canEdit", currentUser.value);
|
|
20
21
|
if (!currentUser.value) return false;
|
|
21
22
|
if (nuxtUsers.auth?.permissions) {
|
|
22
23
|
const userPermissions = nuxtUsers.auth.permissions[currentUser.value.role] || [];
|
|
23
24
|
const apiBasePath = nuxtUsers.apiBasePath;
|
|
25
|
+
console.log("userPermissions", userPermissions);
|
|
26
|
+
console.log("apiBasePath", apiBasePath);
|
|
24
27
|
return userPermissions.some(
|
|
25
|
-
(permission) => permission === "*" || permission === `${apiBasePath}/*` || permission === `${apiBasePath}/[id].
|
|
28
|
+
(permission) => permission === "*" || permission === `${apiBasePath}/*` || permission === `${apiBasePath}/[id].put` || permission === `${apiBasePath}/[id].patch`
|
|
26
29
|
);
|
|
27
30
|
}
|
|
28
31
|
return false;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nuxt-users",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.31.1",
|
|
4
4
|
"description": "A comprehensive user management module for Nuxt 3 and Nuxt 4 applications with authentication, authorization, database support, and CLI tools",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"nuxt",
|
|
@@ -47,7 +47,8 @@
|
|
|
47
47
|
"main": "./dist/module.mjs",
|
|
48
48
|
"types": "./dist/types.d.mts",
|
|
49
49
|
"files": [
|
|
50
|
-
"dist"
|
|
50
|
+
"dist",
|
|
51
|
+
"scripts"
|
|
51
52
|
],
|
|
52
53
|
"bin": {
|
|
53
54
|
"nuxt-users": "./dist/cli.mjs"
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
import { readFileSync, existsSync } from 'node:fs'
|
|
4
|
+
import { join } from 'node:path'
|
|
5
|
+
|
|
6
|
+
const REQUIRED_PEERS = ['bcrypt', 'nodemailer', '@nuxt/kit']
|
|
7
|
+
const OPTIONAL_PEERS = ['nuxt-api-shield']
|
|
8
|
+
|
|
9
|
+
function checkPackageJson() {
|
|
10
|
+
const missing = []
|
|
11
|
+
const optional = []
|
|
12
|
+
|
|
13
|
+
try {
|
|
14
|
+
// Look for package.json in the consumer app (current working directory)
|
|
15
|
+
const pkgPath = join(process.cwd(), 'package.json')
|
|
16
|
+
|
|
17
|
+
if (!existsSync(pkgPath)) {
|
|
18
|
+
console.log('⚠️ Could not find package.json in current directory')
|
|
19
|
+
return { missing: REQUIRED_PEERS, optional: OPTIONAL_PEERS }
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
const pkg = JSON.parse(readFileSync(pkgPath, 'utf8'))
|
|
23
|
+
|
|
24
|
+
// Check all possible dependency locations
|
|
25
|
+
const allDeps = {
|
|
26
|
+
...pkg.dependencies || {},
|
|
27
|
+
...pkg.devDependencies || {},
|
|
28
|
+
...pkg.peerDependencies || {}
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
// Check required dependencies
|
|
32
|
+
for (const dep of REQUIRED_PEERS) {
|
|
33
|
+
if (!allDeps[dep]) {
|
|
34
|
+
missing.push(dep)
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// Check optional dependencies
|
|
39
|
+
for (const dep of OPTIONAL_PEERS) {
|
|
40
|
+
if (!allDeps[dep]) {
|
|
41
|
+
optional.push(dep)
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
return { missing, optional, packageName: pkg.name || 'your project' }
|
|
46
|
+
}
|
|
47
|
+
catch (error) {
|
|
48
|
+
console.log('⚠️ Error reading package.json:', error.message)
|
|
49
|
+
// If we can't read package.json, assume all deps are missing
|
|
50
|
+
return { missing: REQUIRED_PEERS, optional: OPTIONAL_PEERS, packageName: 'your project' }
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
function getPackageManagerCommand() {
|
|
55
|
+
// Detect package manager from lock files or environment
|
|
56
|
+
const cwd = process.cwd()
|
|
57
|
+
|
|
58
|
+
if (existsSync(join(cwd, 'pnpm-lock.yaml'))) {
|
|
59
|
+
return 'pnpm add'
|
|
60
|
+
}
|
|
61
|
+
else if (existsSync(join(cwd, 'yarn.lock'))) {
|
|
62
|
+
return 'yarn add'
|
|
63
|
+
}
|
|
64
|
+
else if (existsSync(join(cwd, 'package-lock.json'))) {
|
|
65
|
+
return 'npm install'
|
|
66
|
+
}
|
|
67
|
+
else if (process.env.npm_config_user_agent?.includes('pnpm')) {
|
|
68
|
+
return 'pnpm add'
|
|
69
|
+
}
|
|
70
|
+
else if (process.env.npm_config_user_agent?.includes('yarn')) {
|
|
71
|
+
return 'yarn add'
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
// Default fallback
|
|
75
|
+
return 'npm install'
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function displayResults({ missing, optional, packageName }) {
|
|
79
|
+
const primaryCmd = getPackageManagerCommand()
|
|
80
|
+
|
|
81
|
+
if (missing.length > 0) {
|
|
82
|
+
console.log('\n🚨 nuxt-users: Missing required peer dependencies!')
|
|
83
|
+
console.log(`Project: ${packageName}`)
|
|
84
|
+
console.log('These dependencies are required for nuxt-users to work properly.\n')
|
|
85
|
+
|
|
86
|
+
console.log('💾 Missing dependencies:')
|
|
87
|
+
missing.forEach(dep => console.log(` - ${dep}`))
|
|
88
|
+
console.log('')
|
|
89
|
+
|
|
90
|
+
console.log('🔧 Install command (detected):')
|
|
91
|
+
console.log(` ${primaryCmd} ${missing.join(' ')}\n`)
|
|
92
|
+
|
|
93
|
+
console.log('🔧 Alternative install commands:')
|
|
94
|
+
console.log(` npm install ${missing.join(' ')}`)
|
|
95
|
+
console.log(` pnpm add ${missing.join(' ')}`)
|
|
96
|
+
console.log(` yarn add ${missing.join(' ')}\n`)
|
|
97
|
+
|
|
98
|
+
console.log('📚 Documentation: https://nuxt-users.webmania.cc/installation')
|
|
99
|
+
console.log('🐛 Issues: https://github.com/rrd108/nuxt-users/issues\n')
|
|
100
|
+
|
|
101
|
+
// Exit with error code to make installation fail
|
|
102
|
+
process.exit(1)
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
if (optional.length > 0 && missing.length === 0) {
|
|
106
|
+
console.log('\n💡 nuxt-users: Optional dependencies available!')
|
|
107
|
+
console.log(`Project: ${packageName}`)
|
|
108
|
+
console.log('These provide additional security and features:\n')
|
|
109
|
+
|
|
110
|
+
console.log('🔒 Optional dependencies:')
|
|
111
|
+
optional.forEach(dep => console.log(` - ${dep}`))
|
|
112
|
+
console.log('')
|
|
113
|
+
|
|
114
|
+
console.log('🔧 Install command (detected):')
|
|
115
|
+
console.log(` ${primaryCmd} ${optional.join(' ')}\n`)
|
|
116
|
+
|
|
117
|
+
console.log('🔧 Alternative install commands:')
|
|
118
|
+
console.log(` npm install ${optional.join(' ')}`)
|
|
119
|
+
console.log(` pnpm add ${optional.join(' ')}`)
|
|
120
|
+
console.log(` yarn add ${optional.join(' ')}\n`)
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
if (missing.length === 0 && optional.length === 0) {
|
|
124
|
+
console.log(`✅ nuxt-users: All dependencies found in ${packageName}!`)
|
|
125
|
+
}
|
|
126
|
+
else if (missing.length === 0) {
|
|
127
|
+
console.log(`✅ nuxt-users: All required dependencies found in ${packageName}!`)
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
async function checkPeerDependencies() {
|
|
132
|
+
const result = checkPackageJson()
|
|
133
|
+
displayResults(result)
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
// Handle both direct execution and module import
|
|
137
|
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
|
138
|
+
checkPeerDependencies().catch(console.error)
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
export { checkPeerDependencies }
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Configuration
|
|
4
|
+
SERVER_HOST="35.198.93.8"
|
|
5
|
+
SERVER_USER="sravanam"
|
|
6
|
+
REMOTE_DOCS_PATH="/var/www/nuxt-users.webmania.cc"
|
|
7
|
+
LOCAL_BUILD_PATH="docs/.vitepress/dist"
|
|
8
|
+
|
|
9
|
+
# Colors for output
|
|
10
|
+
RED='\033[0;31m'
|
|
11
|
+
GREEN='\033[0;32m'
|
|
12
|
+
YELLOW='\033[1;33m'
|
|
13
|
+
NC='\033[0m' # No Color
|
|
14
|
+
|
|
15
|
+
echo -e "${YELLOW}🚀 Starting documentation deployment...${NC}"
|
|
16
|
+
|
|
17
|
+
# Check if build directory exists
|
|
18
|
+
if [ ! -d "$LOCAL_BUILD_PATH" ]; then
|
|
19
|
+
echo -e "${RED}❌ Build directory not found: $LOCAL_BUILD_PATH${NC}"
|
|
20
|
+
echo -e "${YELLOW}💡 Make sure to run 'npm run docs:build' first${NC}"
|
|
21
|
+
exit 1
|
|
22
|
+
fi
|
|
23
|
+
|
|
24
|
+
# Create a temporary tar file for transfer
|
|
25
|
+
TEMP_TAR="docs-build-$(date +%Y%m%d-%H%M%S).tar.gz"
|
|
26
|
+
echo -e "${YELLOW}📦 Creating archive: $TEMP_TAR${NC}"
|
|
27
|
+
tar -czf "$TEMP_TAR" -C "$LOCAL_BUILD_PATH" .
|
|
28
|
+
|
|
29
|
+
# Upload and deploy
|
|
30
|
+
echo -e "${YELLOW}📤 Uploading to $SERVER_HOST...${NC}"
|
|
31
|
+
ssh "$SERVER_USER@$SERVER_HOST" << EOF
|
|
32
|
+
# Create backup of current docs
|
|
33
|
+
if [ -d "$REMOTE_DOCS_PATH" ]; then
|
|
34
|
+
echo "📋 Creating backup of current documentation..."
|
|
35
|
+
cp -r "$REMOTE_DOCS_PATH" "${REMOTE_DOCS_PATH}-backup-\$(date +%Y%m%d-%H%M%S)"
|
|
36
|
+
fi
|
|
37
|
+
|
|
38
|
+
# Create docs directory if it doesn't exist
|
|
39
|
+
mkdir -p "$REMOTE_DOCS_PATH"
|
|
40
|
+
|
|
41
|
+
# Clean the docs directory
|
|
42
|
+
rm -rf "$REMOTE_DOCS_PATH"/*
|
|
43
|
+
|
|
44
|
+
echo "✅ Ready for new files"
|
|
45
|
+
EOF
|
|
46
|
+
|
|
47
|
+
# Copy the tar file to server
|
|
48
|
+
scp "$TEMP_TAR" "$SERVER_USER@$SERVER_HOST:/tmp/"
|
|
49
|
+
|
|
50
|
+
# Extract and deploy on server
|
|
51
|
+
ssh "$SERVER_USER@$SERVER_HOST" << EOF
|
|
52
|
+
echo "📦 Extracting documentation..."
|
|
53
|
+
tar -xzf "/tmp/$TEMP_TAR" -C "$REMOTE_DOCS_PATH"
|
|
54
|
+
|
|
55
|
+
# Set proper permissions
|
|
56
|
+
chmod -R 755 "$REMOTE_DOCS_PATH"
|
|
57
|
+
|
|
58
|
+
# Clean up temporary files
|
|
59
|
+
rm "/tmp/$TEMP_TAR"
|
|
60
|
+
|
|
61
|
+
echo "✅ Documentation deployed successfully!"
|
|
62
|
+
echo "📁 Location: $REMOTE_DOCS_PATH"
|
|
63
|
+
EOF
|
|
64
|
+
|
|
65
|
+
# Clean up local temporary file
|
|
66
|
+
rm "$TEMP_TAR"
|
|
67
|
+
|
|
68
|
+
echo -e "${GREEN}✅ Documentation deployment completed!${NC}"
|
|
69
|
+
echo -e "${YELLOW}🌐 Your docs should now be available on your server${NC}"
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { fileURLToPath } from 'node:url'
|
|
3
|
+
import { dirname, join } from 'node:path'
|
|
4
|
+
import { existsSync, writeFileSync, rmdirSync, unlinkSync, readdirSync, readFileSync } from 'node:fs'
|
|
5
|
+
|
|
6
|
+
const __dirname = dirname(fileURLToPath(import.meta.url))
|
|
7
|
+
const projectRoot = join(__dirname, '..')
|
|
8
|
+
const distDir = join(projectRoot, 'dist')
|
|
9
|
+
const utilsDir = join(distDir, 'utils')
|
|
10
|
+
const utilsIndexFile = join(utilsDir, 'index.js')
|
|
11
|
+
const utilsRootFile = join(distDir, 'utils.js')
|
|
12
|
+
|
|
13
|
+
// Remove existing utils directory if it exists
|
|
14
|
+
if (existsSync(utilsDir)) {
|
|
15
|
+
try {
|
|
16
|
+
if (existsSync(utilsIndexFile)) {
|
|
17
|
+
unlinkSync(utilsIndexFile)
|
|
18
|
+
}
|
|
19
|
+
rmdirSync(utilsDir)
|
|
20
|
+
}
|
|
21
|
+
catch {
|
|
22
|
+
// Ignore errors
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
// Create utils.js in the dist root to handle "../../../utils" imports
|
|
27
|
+
// This allows imports like "../../../utils" to resolve to a file instead of directory
|
|
28
|
+
const rootIndexContent = `export * from './utils.mjs'
|
|
29
|
+
`
|
|
30
|
+
writeFileSync(utilsRootFile, rootIndexContent)
|
|
31
|
+
|
|
32
|
+
// Note: Types imports should be handled by TypeScript compilation, not runtime
|
|
33
|
+
|
|
34
|
+
// Fix import paths in built files to include .js extensions for ES modules
|
|
35
|
+
const runtimeUtilsDir = join(distDir, 'runtime')
|
|
36
|
+
|
|
37
|
+
// Function to recursively find and fix import statements
|
|
38
|
+
function fixImportPaths(dir) {
|
|
39
|
+
const items = readdirSync(dir, { withFileTypes: true })
|
|
40
|
+
|
|
41
|
+
for (const item of items) {
|
|
42
|
+
const fullPath = join(dir, item.name)
|
|
43
|
+
|
|
44
|
+
if (item.isDirectory()) {
|
|
45
|
+
fixImportPaths(fullPath)
|
|
46
|
+
}
|
|
47
|
+
else if (item.isFile() && (item.name.endsWith('.js') || item.name.endsWith('.mjs') || item.name.endsWith('.vue') || item.name.endsWith('.ts'))) {
|
|
48
|
+
let content = readFileSync(fullPath, 'utf8')
|
|
49
|
+
let modified = false
|
|
50
|
+
|
|
51
|
+
// Transform relative imports to utils/imports back to nuxt-users/utils for consumers
|
|
52
|
+
const relativeImportsRegex = /from\s+["'](\.\.[/\\])*utils[/\\]imports["']/g
|
|
53
|
+
if (relativeImportsRegex.test(content)) {
|
|
54
|
+
content = content.replace(relativeImportsRegex, 'from "nuxt-users/utils"')
|
|
55
|
+
modified = true
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
// Transform other relative utils imports
|
|
59
|
+
const utilsImportRegex = /from\s+["']\.\.[/\\]utils[/\\]imports["']/g
|
|
60
|
+
if (utilsImportRegex.test(content)) {
|
|
61
|
+
content = content.replace(utilsImportRegex, 'from "nuxt-users/utils"')
|
|
62
|
+
modified = true
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
if (modified) {
|
|
66
|
+
writeFileSync(fullPath, content)
|
|
67
|
+
console.log(`[Nuxt Users] Transformed import paths in ${fullPath}`)
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
fixImportPaths(runtimeUtilsDir)
|
|
74
|
+
|
|
75
|
+
console.log('[Nuxt Users] Created utils.js file and fixed import paths for ES modules')
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Integration test script for nuxt-users module
|
|
4
|
+
# Tests playground middleware functionality locally
|
|
5
|
+
|
|
6
|
+
set -e
|
|
7
|
+
|
|
8
|
+
echo "🚀 Starting nuxt-users integration tests..."
|
|
9
|
+
|
|
10
|
+
# Colors for output
|
|
11
|
+
RED='\033[0;31m'
|
|
12
|
+
GREEN='\033[0;32m'
|
|
13
|
+
YELLOW='\033[1;33m'
|
|
14
|
+
BLUE='\033[0;34m'
|
|
15
|
+
NC='\033[0m' # No Color
|
|
16
|
+
|
|
17
|
+
# Function to print colored output
|
|
18
|
+
print_status() {
|
|
19
|
+
local color=$1
|
|
20
|
+
local message=$2
|
|
21
|
+
echo -e "${color}${message}${NC}"
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
# Function to cleanup background processes
|
|
25
|
+
cleanup() {
|
|
26
|
+
if [ ! -z "$SERVER_PID" ]; then
|
|
27
|
+
print_status $YELLOW "🧹 Cleaning up server (PID: $SERVER_PID)..."
|
|
28
|
+
kill $SERVER_PID 2>/dev/null || true
|
|
29
|
+
wait $SERVER_PID 2>/dev/null || true
|
|
30
|
+
fi
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
# Set up trap for cleanup on script exit
|
|
34
|
+
trap cleanup EXIT
|
|
35
|
+
|
|
36
|
+
# Check if we're in the right directory
|
|
37
|
+
if [ ! -f "package.json" ] || [ ! -d "playground" ]; then
|
|
38
|
+
print_status $RED "❌ Please run this script from the nuxt-users root directory"
|
|
39
|
+
exit 1
|
|
40
|
+
fi
|
|
41
|
+
|
|
42
|
+
print_status $BLUE "📦 Preparing development environment..."
|
|
43
|
+
|
|
44
|
+
# Prepare the module
|
|
45
|
+
npm run dev:prepare
|
|
46
|
+
|
|
47
|
+
print_status $BLUE "🏗️ Building playground..."
|
|
48
|
+
|
|
49
|
+
# Build the playground
|
|
50
|
+
cd playground
|
|
51
|
+
npm run build
|
|
52
|
+
|
|
53
|
+
print_status $BLUE "🖥️ Starting production server..."
|
|
54
|
+
|
|
55
|
+
# Start the server in background
|
|
56
|
+
node .output/server/index.mjs &
|
|
57
|
+
SERVER_PID=$!
|
|
58
|
+
|
|
59
|
+
# Wait for server to start
|
|
60
|
+
sleep 3
|
|
61
|
+
|
|
62
|
+
# Check if server is running
|
|
63
|
+
if ! kill -0 $SERVER_PID 2>/dev/null; then
|
|
64
|
+
print_status $RED "❌ Server failed to start"
|
|
65
|
+
exit 1
|
|
66
|
+
fi
|
|
67
|
+
|
|
68
|
+
print_status $GREEN "✅ Server started successfully (PID: $SERVER_PID)"
|
|
69
|
+
|
|
70
|
+
# Wait a bit more for server to be fully ready
|
|
71
|
+
sleep 2
|
|
72
|
+
|
|
73
|
+
print_status $BLUE "🧪 Running integration tests..."
|
|
74
|
+
|
|
75
|
+
# Test 1: /me endpoint should require authentication (401 without token)
|
|
76
|
+
print_status $YELLOW "🔐 Testing /me endpoint requires authentication..."
|
|
77
|
+
response=$(curl -s -o /dev/null -w "%{http_code}" "http://localhost:3000/api/nuxt-users/me" || echo "000")
|
|
78
|
+
|
|
79
|
+
if [ "$response" = "401" ]; then
|
|
80
|
+
print_status $GREEN "✅ /me endpoint properly requires authentication (401 without token)"
|
|
81
|
+
else
|
|
82
|
+
print_status $RED "❌ /me endpoint should require authentication - expected 401, got $response"
|
|
83
|
+
print_status $RED " This means server middleware is not properly registered!"
|
|
84
|
+
exit 1
|
|
85
|
+
fi
|
|
86
|
+
|
|
87
|
+
# Test 2: Session endpoint should be accessible (not 401)
|
|
88
|
+
print_status $YELLOW "📝 Testing session endpoint /api/nuxt-users/session..."
|
|
89
|
+
response=$(curl -s -o /dev/null -w "%{http_code}" "http://localhost:3000/api/nuxt-users/session" -X POST || echo "000")
|
|
90
|
+
|
|
91
|
+
if [ "$response" != "401" ]; then
|
|
92
|
+
print_status $GREEN "✅ Session endpoint accessible (HTTP $response - auth not blocking)"
|
|
93
|
+
else
|
|
94
|
+
print_status $RED "❌ Session endpoint blocked by auth - should be accessible for login"
|
|
95
|
+
exit 1
|
|
96
|
+
fi
|
|
97
|
+
|
|
98
|
+
# Test 3: Registration endpoint should be auto-whitelisted
|
|
99
|
+
print_status $YELLOW "📋 Testing registration endpoint /api/nuxt-users/register..."
|
|
100
|
+
response=$(curl -s -o /dev/null -w "%{http_code}" "http://localhost:3000/api/nuxt-users/register" -X POST || echo "000")
|
|
101
|
+
|
|
102
|
+
if [ "$response" != "401" ]; then
|
|
103
|
+
print_status $GREEN "✅ Registration endpoint accessible (HTTP $response - auto-whitelisted)"
|
|
104
|
+
else
|
|
105
|
+
print_status $RED "❌ Registration endpoint blocked - auto-whitelisting not working"
|
|
106
|
+
exit 1
|
|
107
|
+
fi
|
|
108
|
+
|
|
109
|
+
# Test 4: Test a few more protected endpoints if they exist
|
|
110
|
+
print_status $YELLOW "🔍 Testing other protected endpoints..."
|
|
111
|
+
|
|
112
|
+
endpoints=(
|
|
113
|
+
"/api/nuxt-users/profile"
|
|
114
|
+
"/api/nuxt-users/users"
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
for endpoint in "${endpoints[@]}"; do
|
|
118
|
+
response=$(curl -s -o /dev/null -w "%{http_code}" "http://localhost:3000$endpoint" || echo "000")
|
|
119
|
+
|
|
120
|
+
if [ "$response" = "401" ]; then
|
|
121
|
+
print_status $GREEN "✅ $endpoint properly protected (401)"
|
|
122
|
+
elif [ "$response" = "404" ]; then
|
|
123
|
+
print_status $YELLOW "⚠️ $endpoint not found (404) - endpoint may not exist"
|
|
124
|
+
else
|
|
125
|
+
print_status $YELLOW "⚠️ $endpoint returned $response - verify this is expected"
|
|
126
|
+
fi
|
|
127
|
+
done
|
|
128
|
+
|
|
129
|
+
print_status $GREEN "🎉 All integration tests passed!"
|
|
130
|
+
print_status $BLUE "📊 Test Summary:"
|
|
131
|
+
print_status $BLUE " • Server middleware registration: ✅ Working"
|
|
132
|
+
print_status $BLUE " • Authentication enforcement: ✅ Working"
|
|
133
|
+
print_status $BLUE " • Auto-whitelisting: ✅ Working"
|
|
134
|
+
print_status $BLUE " • Endpoint accessibility: ✅ Working"
|
|
135
|
+
|
|
136
|
+
print_status $GREEN "✨ Your nuxt-users module is ready for production!"
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# MySQL Test Runner Script
|
|
4
|
+
# This script sets up environment variables for MySQL testing
|
|
5
|
+
|
|
6
|
+
echo "Setting up MySQL test environment..."
|
|
7
|
+
|
|
8
|
+
# Default MySQL configuration
|
|
9
|
+
export DB_CONNECTOR="mysql"
|
|
10
|
+
export DB_HOST=${DB_HOST:-"localhost"}
|
|
11
|
+
export DB_PORT=${DB_PORT:-"3306"}
|
|
12
|
+
export DB_USER=${DB_USER:-"root"}
|
|
13
|
+
export DB_PASSWORD=${DB_PASSWORD:-"123"}
|
|
14
|
+
export DB_NAME=${DB_NAME:-"test_db"}
|
|
15
|
+
|
|
16
|
+
echo "Database configuration:"
|
|
17
|
+
echo " Host: $DB_HOST"
|
|
18
|
+
echo " Port: $DB_PORT"
|
|
19
|
+
echo " User: $DB_USER"
|
|
20
|
+
echo " Database: $DB_NAME"
|
|
21
|
+
|
|
22
|
+
# Set MySQL password environment variable for consistent authentication
|
|
23
|
+
export MYSQL_PWD="$DB_PASSWORD"
|
|
24
|
+
|
|
25
|
+
# Wait for MySQL to be ready
|
|
26
|
+
echo "Waiting for MySQL connection..."
|
|
27
|
+
for i in {1..10}; do
|
|
28
|
+
if mysql -h"$DB_HOST" -P"$DB_PORT" -u"$DB_USER" -e "SELECT 1;" >/dev/null 2>&1; then
|
|
29
|
+
echo "MySQL connection successful!"
|
|
30
|
+
break
|
|
31
|
+
fi
|
|
32
|
+
echo "MySQL not ready, retrying in 3 seconds... (attempt $i/10)"
|
|
33
|
+
sleep 3
|
|
34
|
+
done
|
|
35
|
+
|
|
36
|
+
# Final check if MySQL is running
|
|
37
|
+
if ! mysql -h"$DB_HOST" -P"$DB_PORT" -u"$DB_USER" -e "SELECT 1;" >/dev/null 2>&1; then
|
|
38
|
+
echo "Error: Cannot connect to MySQL after multiple retries. Please ensure MySQL is running and accessible."
|
|
39
|
+
echo "You can start MySQL with: docker run --name mysql-test -e MYSQL_ROOT_PASSWORD=123 -e MYSQL_DATABASE=test_db -p 3306:3306 -d mysql:5.7"
|
|
40
|
+
exit 1
|
|
41
|
+
fi
|
|
42
|
+
|
|
43
|
+
# Create test database if it doesn't exist
|
|
44
|
+
mysql -h"$DB_HOST" -P"$DB_PORT" -u"$DB_USER" -e "CREATE DATABASE IF NOT EXISTS $DB_NAME;" >/dev/null 2>&1
|
|
45
|
+
|
|
46
|
+
echo "Running tests against MySQL..."
|
|
47
|
+
|
|
48
|
+
# Check if any arguments were passed
|
|
49
|
+
if [ $# -eq 0 ]; then
|
|
50
|
+
# Run all tests except unit tests (database-independent)
|
|
51
|
+
vitest run --exclude="test/unit/"
|
|
52
|
+
else
|
|
53
|
+
vitest run "$@"
|
|
54
|
+
fi
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# PostgreSQL Test Runner Script
|
|
4
|
+
# This script sets up environment variables for PostgreSQL testing
|
|
5
|
+
|
|
6
|
+
echo "Setting up PostgreSQL test environment..."
|
|
7
|
+
|
|
8
|
+
# Default PostgreSQL configuration
|
|
9
|
+
export DB_CONNECTOR="postgresql"
|
|
10
|
+
export DB_HOST=${DB_HOST:-"localhost"}
|
|
11
|
+
export DB_PORT=${DB_PORT:-"5432"}
|
|
12
|
+
export DB_USER=${DB_USER:-"postgres"}
|
|
13
|
+
export DB_PASSWORD=${DB_PASSWORD:-"123"}
|
|
14
|
+
export DB_NAME=${DB_NAME:-"test_db"}
|
|
15
|
+
|
|
16
|
+
echo "Database configuration:"
|
|
17
|
+
echo " Host: $DB_HOST"
|
|
18
|
+
echo " Port: $DB_PORT"
|
|
19
|
+
echo " User: $DB_USER"
|
|
20
|
+
echo " Database: $DB_NAME"
|
|
21
|
+
|
|
22
|
+
# Wait for PostgreSQL to be ready
|
|
23
|
+
echo "Waiting for PostgreSQL connection..."
|
|
24
|
+
for i in {1..10}; do
|
|
25
|
+
if pg_isready -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -q; then
|
|
26
|
+
echo "PostgreSQL connection successful!"
|
|
27
|
+
break
|
|
28
|
+
fi
|
|
29
|
+
echo "PostgreSQL not ready, retrying in 3 seconds... (attempt $i/10)"
|
|
30
|
+
sleep 3
|
|
31
|
+
done
|
|
32
|
+
|
|
33
|
+
# Final check if PostgreSQL is running
|
|
34
|
+
if ! pg_isready -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -q; then
|
|
35
|
+
echo "Error: Cannot connect to PostgreSQL after multiple retries. Please ensure PostgreSQL is running and accessible."
|
|
36
|
+
echo "You can start PostgreSQL with: docker run --name postgres-test -e POSTGRES_PASSWORD=123 -e POSTGRES_DB=test_db -p 5432:5432 -d postgres:13"
|
|
37
|
+
exit 1
|
|
38
|
+
fi
|
|
39
|
+
|
|
40
|
+
# Recreate the test database to ensure a clean state
|
|
41
|
+
echo "Recreating test database '$DB_NAME'..."
|
|
42
|
+
|
|
43
|
+
# Drop database if exists (ignore errors)
|
|
44
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d postgres -c "DROP DATABASE IF EXISTS \"$DB_NAME\";" >/dev/null 2>&1
|
|
45
|
+
|
|
46
|
+
# Create database with proper encoding to avoid collation issues
|
|
47
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d postgres -c "CREATE DATABASE \"$DB_NAME\" WITH ENCODING 'UTF8' LC_COLLATE='C' LC_CTYPE='C';" >/dev/null 2>&1
|
|
48
|
+
|
|
49
|
+
# Verify database was created
|
|
50
|
+
if ! PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "SELECT 1;" >/dev/null 2>&1; then
|
|
51
|
+
echo "Error: Failed to create or connect to database '$DB_NAME'"
|
|
52
|
+
echo "Trying alternative approach..."
|
|
53
|
+
|
|
54
|
+
# Try creating with template0 to avoid collation issues
|
|
55
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d postgres -c "CREATE DATABASE \"$DB_NAME\" TEMPLATE template0;" >/dev/null 2>&1
|
|
56
|
+
|
|
57
|
+
if ! PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "SELECT 1;" >/dev/null 2>&1; then
|
|
58
|
+
echo "Error: Still cannot create database. Please check PostgreSQL configuration."
|
|
59
|
+
exit 1
|
|
60
|
+
fi
|
|
61
|
+
fi
|
|
62
|
+
|
|
63
|
+
echo "Database '$DB_NAME' created successfully!"
|
|
64
|
+
|
|
65
|
+
# Wait a moment for database to be ready
|
|
66
|
+
sleep 2
|
|
67
|
+
|
|
68
|
+
# Configure PostgreSQL for testing (increase connection limits)
|
|
69
|
+
echo "Configuring PostgreSQL for testing..."
|
|
70
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "ALTER SYSTEM SET max_connections = 500;" >/dev/null 2>&1
|
|
71
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "ALTER SYSTEM SET shared_preload_libraries = 'pg_stat_statements';" >/dev/null 2>&1
|
|
72
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "ALTER SYSTEM SET log_statement = 'none';" >/dev/null 2>&1
|
|
73
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "ALTER SYSTEM SET log_min_duration_statement = -1;" >/dev/null 2>&1
|
|
74
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "ALTER SYSTEM SET idle_in_transaction_session_timeout = '10s';" >/dev/null 2>&1
|
|
75
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "SELECT pg_reload_conf();" >/dev/null 2>&1
|
|
76
|
+
|
|
77
|
+
# Kill any idle connections to free up slots
|
|
78
|
+
echo "Cleaning up idle connections..."
|
|
79
|
+
PGPASSWORD="$DB_PASSWORD" psql -h "$DB_HOST" -p "$DB_PORT" -U "$DB_USER" -d "$DB_NAME" -c "
|
|
80
|
+
SELECT pg_terminate_backend(pid)
|
|
81
|
+
FROM pg_stat_activity
|
|
82
|
+
WHERE state IN ('idle', 'idle in transaction') AND pid <> pg_backend_pid();
|
|
83
|
+
" >/dev/null 2>&1
|
|
84
|
+
|
|
85
|
+
echo "Running tests against PostgreSQL..."
|
|
86
|
+
|
|
87
|
+
# Check if any arguments were passed
|
|
88
|
+
if [ $# -eq 0 ]; then
|
|
89
|
+
# Run all tests except unit tests (database-independent)
|
|
90
|
+
vitest run --exclude="test/unit/"
|
|
91
|
+
else
|
|
92
|
+
vitest run "$@"
|
|
93
|
+
fi
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# SQLite Test Runner Script
|
|
4
|
+
# This script sets up environment variables for SQLite testing
|
|
5
|
+
|
|
6
|
+
echo "Setting up SQLite test environment..."
|
|
7
|
+
|
|
8
|
+
# Force SQLite configuration
|
|
9
|
+
export DB_CONNECTOR="sqlite"
|
|
10
|
+
|
|
11
|
+
echo "Database configuration:"
|
|
12
|
+
echo " Type: SQLite"
|
|
13
|
+
echo " Path: ./_test-db (default)"
|
|
14
|
+
|
|
15
|
+
echo "Running tests against SQLite..."
|
|
16
|
+
|
|
17
|
+
# Check if any arguments were passed
|
|
18
|
+
if [ $# -eq 0 ]; then
|
|
19
|
+
# Run all tests except unit tests (database-independent)
|
|
20
|
+
vitest run --exclude="test/unit/"
|
|
21
|
+
else
|
|
22
|
+
vitest run "$@"
|
|
23
|
+
fi
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
|
|
3
|
+
# Unit Test Runner Script
|
|
4
|
+
# This script runs tests that don't require database access
|
|
5
|
+
|
|
6
|
+
echo "Running unit tests (no database required)..."
|
|
7
|
+
|
|
8
|
+
# Check if any arguments were passed
|
|
9
|
+
if [ $# -eq 0 ]; then
|
|
10
|
+
# Run all unit tests
|
|
11
|
+
vitest run test/unit/
|
|
12
|
+
else
|
|
13
|
+
# Run only the specified test
|
|
14
|
+
vitest run "$@"
|
|
15
|
+
fi
|