newo 1.6.0 → 1.7.0
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 +94 -0
- package/README.md +1 -1
- package/dist/api.d.ts +3 -1
- package/dist/api.js +21 -0
- package/dist/cli.js +6 -1
- package/dist/fsutil.d.ts +8 -0
- package/dist/fsutil.js +29 -0
- package/dist/sync.d.ts +1 -0
- package/dist/sync.js +313 -50
- package/dist/types.d.ts +61 -6
- package/package.json +2 -2
- package/src/api.ts +31 -6
- package/src/cli.ts +5 -1
- package/src/fsutil.ts +60 -4
- package/src/sync.ts +393 -85
- package/src/types.ts +69 -6
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,100 @@ All notable changes to this project will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [1.7.0] - 2025-09-15
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
- **Customer Attributes Synchronization**: Complete pull/push functionality for customer attributes
|
|
12
|
+
- `GET /api/v1/bff/customer/attributes?include_hidden=true` - Fetches all 233 customer attributes including hidden system attributes
|
|
13
|
+
- `PUT /api/v1/customer/attributes/{attributeId}` - Updates individual customer attributes
|
|
14
|
+
- Saves to `newo_customers/{customerIdn}/attributes.yaml` in customer root directory
|
|
15
|
+
- YAML format matches reference specification exactly with literal blocks, enum types, and proper multi-line formatting
|
|
16
|
+
- Separate ID mapping stored in `.newo/{customerIdn}/attributes-map.json` for push operations
|
|
17
|
+
- Integrated into existing `pull` and `push` commands seamlessly
|
|
18
|
+
- Full TypeScript type safety with `CustomerAttribute` and `CustomerAttributesResponse` interfaces
|
|
19
|
+
|
|
20
|
+
### Enhanced
|
|
21
|
+
- **YAML Format Compliance**: Perfect format matching with reference files
|
|
22
|
+
- Literal block scalars (`|-`) for multi-line strings
|
|
23
|
+
- Proper enum format (`!enum "AttributeValueTypes.string"`)
|
|
24
|
+
- Complex JSON string formatting with proper line breaks
|
|
25
|
+
- No escaped quotes in output for better readability
|
|
26
|
+
- **Metadata Generation**: Removed legacy JSON metadata files, YAML-only approach
|
|
27
|
+
- Eliminates redundant `metadata.json` files
|
|
28
|
+
- Cleaner file structure with single source of truth
|
|
29
|
+
- Improved performance with fewer file operations
|
|
30
|
+
|
|
31
|
+
### Technical
|
|
32
|
+
- **API Layer**: Added `updateCustomerAttribute()` and enhanced `getCustomerAttributes()` with `includeHidden` parameter
|
|
33
|
+
- **Sync Engine**: Integrated attributes handling into `pullAll()` and `pushChanged()` functions
|
|
34
|
+
- **File System**: Added `customerAttributesPath()` and `customerAttributesMapPath()` utilities
|
|
35
|
+
- **Type Safety**: Extended type definitions with proper customer attribute interfaces
|
|
36
|
+
- **Error Handling**: Comprehensive error handling for attributes operations with graceful fallbacks
|
|
37
|
+
|
|
38
|
+
## [1.6.1] - 2025-09-13
|
|
39
|
+
|
|
40
|
+
### Fixed
|
|
41
|
+
- **YAML Enum Formatting**: Fixed enum formatting in `flows.yaml` generation to properly handle NEWO enum types
|
|
42
|
+
- Corrected enum value serialization from quoted strings to proper YAML enum format
|
|
43
|
+
- Fixed issue where enum values like `!enum "RunnerType.guidance"` were incorrectly quoted
|
|
44
|
+
- Ensures generated `flows.yaml` files are properly formatted for NEWO platform consumption
|
|
45
|
+
|
|
46
|
+
### Enhanced
|
|
47
|
+
- **ES Module Support**: Added `"type": "module"` to package.json for proper ES module handling
|
|
48
|
+
- Resolves Node.js warnings about module type detection
|
|
49
|
+
- Improves performance by eliminating module type guessing
|
|
50
|
+
- Ensures consistent ES module behavior across all environments
|
|
51
|
+
|
|
52
|
+
## [1.6.0] - 2025-09-13
|
|
53
|
+
|
|
54
|
+
### Added
|
|
55
|
+
- **Multi-Customer Auto-Pull**: Revolutionary workflow improvement for multi-customer environments
|
|
56
|
+
- `newo pull` now automatically pulls from ALL customers when no default customer is set
|
|
57
|
+
- Eliminates the need to specify `--customer` flag or set `NEWO_DEFAULT_CUSTOMER` for bulk operations
|
|
58
|
+
- Maintains backward compatibility - individual customer selection still works with `--customer` flag
|
|
59
|
+
- Smart detection: single customer setup works as before, multi-customer setup auto-pulls all
|
|
60
|
+
- **Publishing Infrastructure**: Complete automated publishing system for professional releases
|
|
61
|
+
- `scripts/publish-github.sh`: Automated GitHub publishing with releases, tags, and version management
|
|
62
|
+
- `scripts/publish-npm.sh`: Automated NPM publishing with validation and safety checks
|
|
63
|
+
- Comprehensive Makefile with 40+ commands for development and publishing workflows
|
|
64
|
+
- Version bump helpers (patch/minor/major) with semantic versioning support
|
|
65
|
+
- **Enhanced Documentation**: Professional publishing and development documentation
|
|
66
|
+
- Complete "Publishing & Release Management" section with step-by-step workflows
|
|
67
|
+
- "Local Testing" section with comprehensive testing procedures
|
|
68
|
+
- Makefile command reference with organized development workflows
|
|
69
|
+
- Troubleshooting guides for common development and publishing issues
|
|
70
|
+
|
|
71
|
+
### Enhanced
|
|
72
|
+
- **Customer Configuration Logic**: New functions for flexible customer handling
|
|
73
|
+
- `tryGetDefaultCustomer()`: Non-throwing version that returns null for multi-customer scenarios
|
|
74
|
+
- `getAllCustomers()`: Returns array of all configured customers for batch operations
|
|
75
|
+
- Improved error handling and user feedback for customer selection scenarios
|
|
76
|
+
- **CLI User Experience**: Enhanced command behavior and help documentation
|
|
77
|
+
- Updated help text to reflect auto-pull behavior: "uses default or all for pull"
|
|
78
|
+
- Clear progress indicators for multi-customer operations
|
|
79
|
+
- Better error messages and troubleshooting guidance
|
|
80
|
+
- **Development Workflow**: Professional development and publishing infrastructure
|
|
81
|
+
- Makefile with color-coded output and comprehensive command organization
|
|
82
|
+
- Automated validation pipelines for publishing (build, test, lint, typecheck)
|
|
83
|
+
- Publishing scripts with safety checks and rollback procedures
|
|
84
|
+
|
|
85
|
+
### Changed
|
|
86
|
+
- **Pull Command Behavior**: Breaking change in multi-customer environments (improvement)
|
|
87
|
+
- Previously: Required explicit customer selection or default customer configuration
|
|
88
|
+
- Now: Automatically pulls from all customers when no default is set
|
|
89
|
+
- Single customer setups: No change in behavior
|
|
90
|
+
- Multi-customer setups: Significantly improved user experience
|
|
91
|
+
- **Help Documentation**: Updated command descriptions and examples
|
|
92
|
+
- `newo pull` now shows "(all customers if no default)" in help text
|
|
93
|
+
- Enhanced multi-customer examples with auto-pull scenarios
|
|
94
|
+
- Updated usage patterns to reflect new workflow capabilities
|
|
95
|
+
|
|
96
|
+
### Developer Experience
|
|
97
|
+
- **Publishing Automation**: One-command publishing to both GitHub and NPM with full validation
|
|
98
|
+
- **Comprehensive Testing**: Enhanced local testing documentation with step-by-step procedures
|
|
99
|
+
- **Professional Infrastructure**: Industry-standard publishing pipeline with version management
|
|
100
|
+
- **Quality Gates**: Automated validation before publishing (TypeScript, linting, building, package validation)
|
|
101
|
+
|
|
8
102
|
## [1.5.2] - 2025-01-15
|
|
9
103
|
|
|
10
104
|
### Enhanced
|
package/README.md
CHANGED
package/dist/api.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { type AxiosInstance } from 'axios';
|
|
2
|
-
import type { ProjectMeta, Agent, Skill, FlowEvent, FlowState, AkbImportArticle, CustomerProfile } from './types.js';
|
|
2
|
+
import type { ProjectMeta, Agent, Skill, FlowEvent, FlowState, AkbImportArticle, CustomerProfile, CustomerAttribute, CustomerAttributesResponse } from './types.js';
|
|
3
3
|
export declare function makeClient(verbose?: boolean, token?: string): Promise<AxiosInstance>;
|
|
4
4
|
export declare function listProjects(client: AxiosInstance): Promise<ProjectMeta[]>;
|
|
5
5
|
export declare function listAgents(client: AxiosInstance, projectId: string): Promise<Agent[]>;
|
|
@@ -11,4 +11,6 @@ export declare function listFlowEvents(client: AxiosInstance, flowId: string): P
|
|
|
11
11
|
export declare function listFlowStates(client: AxiosInstance, flowId: string): Promise<FlowState[]>;
|
|
12
12
|
export declare function importAkbArticle(client: AxiosInstance, articleData: AkbImportArticle): Promise<unknown>;
|
|
13
13
|
export declare function getCustomerProfile(client: AxiosInstance): Promise<CustomerProfile>;
|
|
14
|
+
export declare function getCustomerAttributes(client: AxiosInstance, includeHidden?: boolean): Promise<CustomerAttributesResponse>;
|
|
15
|
+
export declare function updateCustomerAttribute(client: AxiosInstance, attribute: CustomerAttribute): Promise<void>;
|
|
14
16
|
//# sourceMappingURL=api.d.ts.map
|
package/dist/api.js
CHANGED
|
@@ -100,4 +100,25 @@ export async function getCustomerProfile(client) {
|
|
|
100
100
|
const response = await client.get('/api/v1/customer/profile');
|
|
101
101
|
return response.data;
|
|
102
102
|
}
|
|
103
|
+
export async function getCustomerAttributes(client, includeHidden = true) {
|
|
104
|
+
const response = await client.get('/api/v1/bff/customer/attributes', {
|
|
105
|
+
params: { include_hidden: includeHidden }
|
|
106
|
+
});
|
|
107
|
+
return response.data;
|
|
108
|
+
}
|
|
109
|
+
export async function updateCustomerAttribute(client, attribute) {
|
|
110
|
+
if (!attribute.id) {
|
|
111
|
+
throw new Error(`Attribute ${attribute.idn} is missing ID - cannot update`);
|
|
112
|
+
}
|
|
113
|
+
await client.put(`/api/v1/customer/attributes/${attribute.id}`, {
|
|
114
|
+
idn: attribute.idn,
|
|
115
|
+
value: attribute.value,
|
|
116
|
+
title: attribute.title,
|
|
117
|
+
description: attribute.description,
|
|
118
|
+
group: attribute.group,
|
|
119
|
+
is_hidden: attribute.is_hidden,
|
|
120
|
+
possible_values: attribute.possible_values,
|
|
121
|
+
value_type: attribute.value_type
|
|
122
|
+
});
|
|
123
|
+
}
|
|
103
124
|
//# sourceMappingURL=api.js.map
|
package/dist/cli.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import minimist from 'minimist';
|
|
3
3
|
import dotenv from 'dotenv';
|
|
4
4
|
import { makeClient, getProjectMeta, importAkbArticle } from './api.js';
|
|
5
|
-
import { pullAll, pushChanged, status } from './sync.js';
|
|
5
|
+
import { pullAll, pushChanged, status, saveCustomerAttributes } from './sync.js';
|
|
6
6
|
import { parseAkbFile, prepareArticlesForImport } from './akb.js';
|
|
7
7
|
import { initializeEnvironment, ENV, EnvValidationError } from './env.js';
|
|
8
8
|
import { parseCustomerConfigAsync, listCustomers, getCustomer, getDefaultCustomer, tryGetDefaultCustomer, getAllCustomers, validateCustomerConfig } from './customerAsync.js';
|
|
@@ -278,6 +278,11 @@ File Structure:
|
|
|
278
278
|
const meta = await getProjectMeta(client, selectedCustomer.projectId);
|
|
279
279
|
console.log(JSON.stringify(meta, null, 2));
|
|
280
280
|
}
|
|
281
|
+
else if (cmd === 'pull-attributes') {
|
|
282
|
+
console.log(`🔍 Fetching customer attributes for ${selectedCustomer.idn}...`);
|
|
283
|
+
await saveCustomerAttributes(client, selectedCustomer, verbose);
|
|
284
|
+
console.log(`✅ Customer attributes saved to newo_customers/${selectedCustomer.idn}/attributes.yaml`);
|
|
285
|
+
}
|
|
281
286
|
else if (cmd === 'import-akb') {
|
|
282
287
|
const akbFile = args._[1];
|
|
283
288
|
const personaId = args._[2];
|
package/dist/fsutil.d.ts
CHANGED
|
@@ -9,7 +9,15 @@ export declare function hashesPath(customerIdn: string): string;
|
|
|
9
9
|
export declare function ensureState(customerIdn: string): Promise<void>;
|
|
10
10
|
export declare function projectDir(customerIdn: string, projectIdn: string): string;
|
|
11
11
|
export declare function flowsYamlPath(customerIdn: string): string;
|
|
12
|
+
export declare function customerAttributesPath(customerIdn: string): string;
|
|
13
|
+
export declare function customerAttributesMapPath(customerIdn: string): string;
|
|
12
14
|
export declare function skillPath(customerIdn: string, projectIdn: string, agentIdn: string, flowIdn: string, skillIdn: string, runnerType?: RunnerType): string;
|
|
15
|
+
export declare function skillFolderPath(customerIdn: string, projectIdn: string, agentIdn: string, flowIdn: string, skillIdn: string): string;
|
|
16
|
+
export declare function skillScriptPath(customerIdn: string, projectIdn: string, agentIdn: string, flowIdn: string, skillIdn: string, runnerType?: RunnerType): string;
|
|
17
|
+
export declare function projectMetadataPath(customerIdn: string, projectIdn: string): string;
|
|
18
|
+
export declare function agentMetadataPath(customerIdn: string, projectIdn: string, agentIdn: string): string;
|
|
19
|
+
export declare function flowMetadataPath(customerIdn: string, projectIdn: string, agentIdn: string, flowIdn: string): string;
|
|
20
|
+
export declare function skillMetadataPath(customerIdn: string, projectIdn: string, agentIdn: string, flowIdn: string, skillIdn: string): string;
|
|
13
21
|
export declare function metadataPath(customerIdn: string, projectIdn: string): string;
|
|
14
22
|
export declare const ROOT_DIR: string;
|
|
15
23
|
export declare const MAP_PATH: string;
|
package/dist/fsutil.js
CHANGED
|
@@ -28,10 +28,39 @@ export function projectDir(customerIdn, projectIdn) {
|
|
|
28
28
|
export function flowsYamlPath(customerIdn) {
|
|
29
29
|
return path.posix.join(customerProjectsDir(customerIdn), 'flows.yaml');
|
|
30
30
|
}
|
|
31
|
+
export function customerAttributesPath(customerIdn) {
|
|
32
|
+
return path.posix.join(customerDir(customerIdn), 'attributes.yaml');
|
|
33
|
+
}
|
|
34
|
+
export function customerAttributesMapPath(customerIdn) {
|
|
35
|
+
return path.join(customerStateDir(customerIdn), 'attributes-map.json');
|
|
36
|
+
}
|
|
37
|
+
// Legacy skill path - direct file
|
|
31
38
|
export function skillPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn, runnerType = 'guidance') {
|
|
32
39
|
const extension = runnerType === 'nsl' ? '.jinja' : '.guidance';
|
|
33
40
|
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, agentIdn, flowIdn, `${skillIdn}${extension}`);
|
|
34
41
|
}
|
|
42
|
+
// New hierarchical structure paths
|
|
43
|
+
export function skillFolderPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn) {
|
|
44
|
+
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, agentIdn, flowIdn, skillIdn);
|
|
45
|
+
}
|
|
46
|
+
export function skillScriptPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn, runnerType = 'guidance') {
|
|
47
|
+
const extension = runnerType === 'nsl' ? '.jinja' : '.guidance';
|
|
48
|
+
return path.posix.join(skillFolderPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn), `skill${extension}`);
|
|
49
|
+
}
|
|
50
|
+
// Metadata paths for hierarchical structure
|
|
51
|
+
export function projectMetadataPath(customerIdn, projectIdn) {
|
|
52
|
+
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, 'metadata.yaml');
|
|
53
|
+
}
|
|
54
|
+
export function agentMetadataPath(customerIdn, projectIdn, agentIdn) {
|
|
55
|
+
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, agentIdn, 'metadata.yaml');
|
|
56
|
+
}
|
|
57
|
+
export function flowMetadataPath(customerIdn, projectIdn, agentIdn, flowIdn) {
|
|
58
|
+
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, agentIdn, flowIdn, 'metadata.yaml');
|
|
59
|
+
}
|
|
60
|
+
export function skillMetadataPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn) {
|
|
61
|
+
return path.posix.join(skillFolderPath(customerIdn, projectIdn, agentIdn, flowIdn, skillIdn), 'metadata.yaml');
|
|
62
|
+
}
|
|
63
|
+
// Legacy metadata path - keep for backwards compatibility
|
|
35
64
|
export function metadataPath(customerIdn, projectIdn) {
|
|
36
65
|
return path.posix.join(customerProjectsDir(customerIdn), projectIdn, 'metadata.json');
|
|
37
66
|
}
|
package/dist/sync.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { AxiosInstance } from 'axios';
|
|
2
2
|
import type { ProjectData, CustomerConfig } from './types.js';
|
|
3
|
+
export declare function saveCustomerAttributes(client: AxiosInstance, customer: CustomerConfig, verbose?: boolean): Promise<void>;
|
|
3
4
|
export declare function pullSingleProject(client: AxiosInstance, customer: CustomerConfig, projectId: string, projectIdn: string, verbose?: boolean): Promise<ProjectData>;
|
|
4
5
|
export declare function pullAll(client: AxiosInstance, customer: CustomerConfig, projectId?: string | null, verbose?: boolean): Promise<void>;
|
|
5
6
|
export declare function pushChanged(client: AxiosInstance, customer: CustomerConfig, verbose?: boolean): Promise<void>;
|