UNPKG

n8n-nodes-awx

Version:

n8n node to interact with Ansible AWX/Tower with improved type safety

283 lines 11.4 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); const HostResources_1 = require("../src/resources/HostResources"); const mockApiClient = { get: jest.fn(), post: jest.fn(), put: jest.fn(), delete: jest.fn(), }; const createMockHost = (overrides = {}) => ({ id: 1, type: 'host', url: '/api/v2/hosts/1/', related: { created_by: '/api/v2/users/1/', modified_by: '/api/v2/users/1/', variable_data: {}, inventory: '/api/v2/inventories/1/', groups: '/api/v2/hosts/1/groups/', all_groups: '/api/v2/hosts/1/all_groups/', job_events: '/api/v2/hosts/1/job_events/', job_host_summaries: '/api/v2/hosts/1/job_host_summaries/', activity_stream: '/api/v2/hosts/1/activity_stream/', }, summary_fields: { inventory: { id: 1, name: 'Test Inventory', description: 'Test inventory for unit testing', }, created_by: { id: 1, username: 'admin', first_name: '', last_name: '', }, modified_by: { id: 1, username: 'admin', first_name: '', last_name: '', }, user_capabilities: { edit: true, delete: true, }, }, created: '2023-01-01T00:00:00.000Z', modified: '2023-01-01T00:00:00.000Z', name: 'test-host', description: 'Test host', inventory: 1, enabled: true, instance_id: '', variables: '{}', has_active_failures: false, has_inventory_sources: false, last_job: null, last_job_host_summary: null, ansible_facts: {}, ansible_facts_modified: null, ...overrides, }); describe('HostResources', () => { let hostResources; beforeEach(() => { jest.clearAllMocks(); hostResources = new HostResources_1.HostResources(mockApiClient); mockApiClient.get.mockImplementation((url) => { if (url.includes('/api/v2/hosts/')) { if (url.includes('name=')) { return Promise.resolve({ data: { count: 1, next: null, previous: null, results: [createMockHost()] } }); } else if (url.match(/\/api\/v2\/hosts\/\d+\/$/)) { return Promise.resolve({ data: createMockHost() }); } return Promise.resolve({ data: { count: 1, next: null, previous: null, results: [createMockHost()] } }); } return Promise.resolve({ data: createMockHost() }); }); mockApiClient.post.mockImplementation(() => { return Promise.resolve({ data: createMockHost({ id: 2, name: 'New Host' }) }); }); mockApiClient.put.mockImplementation(() => { return Promise.resolve({ data: createMockHost({ name: 'Updated Host' }) }); }); mockApiClient.delete.mockImplementation(() => { return Promise.resolve(); }); }); describe('list', () => { it('should list all hosts', async () => { const hosts = await hostResources.list(); expect(Array.isArray(hosts)).toBe(true); expect(hosts.length).toBeGreaterThan(0); expect(hosts[0]).toHaveProperty('id'); expect(hosts[0]).toHaveProperty('name'); expect(hosts[0]).toHaveProperty('inventory'); expect(mockApiClient.get).toHaveBeenCalledWith('/api/v2/hosts/'); }); it('should pass query parameters to the API', async () => { const params = { inventory: 1 }; await hostResources.list(params); expect(mockApiClient.get).toHaveBeenCalledWith(expect.stringContaining('inventory=1')); }); }); describe('get', () => { it('should get a host by ID', async () => { const host = await hostResources.get(1); expect(host).toBeDefined(); expect(host.id).toBe(1); expect(mockApiClient.get).toHaveBeenCalledWith('/api/v2/hosts/1/'); }); it('should throw an error when ID is not provided', async () => { await expect(hostResources.get(0)).rejects.toThrow('Host ID is required'); }); }); describe('getByName', () => { it('should get a host by name', async () => { const host = await hostResources.getByName('test-host'); expect(host).toBeDefined(); expect(host === null || host === void 0 ? void 0 : host.id).toBe(1); expect(mockApiClient.get).toHaveBeenCalledWith('/api/v2/hosts/?name=test-host'); }); it('should return null when no host is found', async () => { mockApiClient.get.mockResolvedValueOnce({ data: { count: 0, next: null, previous: null, results: [] } }); const host = await hostResources.getByName('nonexistent-host'); expect(host).toBeNull(); }); it('should throw an error when multiple hosts are found', async () => { mockApiClient.get.mockResolvedValueOnce({ data: { count: 2, next: null, previous: null, results: [ createMockHost({ id: 1, name: 'duplicate-host' }), createMockHost({ id: 2, name: 'duplicate-host' }) ] } }); await expect(hostResources.getByName('duplicate-host')) .rejects.toThrow('Multiple hosts found with name: duplicate-host'); }); it('should include inventory ID in the request when provided', async () => { await hostResources.getByName('test-host', 123); expect(mockApiClient.get).toHaveBeenCalledWith('/api/v2/hosts/?name=test-host&inventory=123'); }); }); describe('create', () => { it('should create a new host', async () => { const hostData = { name: 'new-host', inventory: 1, description: 'New test host', enabled: true, variables: '{}' }; const host = await hostResources.create(hostData); expect(host).toBeDefined(); expect(host.name).toBe('New Host'); expect(host.id).toBe(2); expect(mockApiClient.post).toHaveBeenCalledWith('/api/v2/hosts/', hostData); }); it('should require name and inventory', async () => { const invalidHostData = { description: 'Missing required fields' }; await expect(hostResources.create(invalidHostData)).rejects.toThrow('Missing required fields: name, inventory'); }); }); describe('update', () => { it('should update an existing host', async () => { const updateData = { name: 'updated-host' }; const host = await hostResources.update(1, updateData); expect(host).toBeDefined(); expect(host.name).toBe('Updated Host'); expect(mockApiClient.put).toHaveBeenCalledWith('/api/v2/hosts/1/', updateData); }); it('should throw an error when ID is not provided', async () => { await expect(hostResources.update(0, {})).rejects.toThrow('Host ID is required'); }); }); describe('delete', () => { it('should delete a host', async () => { await hostResources.delete(1); expect(mockApiClient.delete).toHaveBeenCalledWith('/api/v2/hosts/1/'); }); it('should throw an error when ID is not provided', async () => { await expect(hostResources.delete(0)).rejects.toThrow('Host ID is required'); }); }); describe('buildUrl', () => { const testBuildUrl = (hostResources, path, params) => { const resourcesWithPrivate = hostResources; return resourcesWithPrivate.buildUrl(path, params); }; it('should return the base URL when no params are provided', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/'); expect(result).toBe('/api/v2/hosts/'); }); it('should handle empty params object', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/', {}); expect(result).toBe('/api/v2/hosts/'); }); it('should handle undefined and null params', () => { const result1 = testBuildUrl(hostResources, '/api/v2/hosts/', undefined); expect(result1).toBe('/api/v2/hosts/'); const result2 = testBuildUrl(hostResources, '/api/v2/hosts/', null); expect(result2).toBe('/api/v2/hosts/'); }); it('should append query parameters correctly', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/', { name: 'test host', inventory: 1, page: 1, page_size: 10 }); expect(result).toContain('name=test%20host'); expect(result).toContain('inventory=1'); expect(result).toContain('page=1'); expect(result).toContain('page_size=10'); expect(result).toMatch(/^\/api\/v2\/hosts\/\?.*/); }); it('should handle special characters in parameters', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/', { name: 'host@test', description: 'Test host with special chars & spaces' }); expect(result).toContain('name=host%40test'); expect(result).toContain('description=Test%20host%20with%20special%20chars%20%26%20spaces'); }); it('should filter out undefined, null, and empty string values', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/', { name: 'test', status: undefined, description: null, inventory: 0, emptyString: '' }); expect(result).toContain('name=test'); expect(result).toContain('inventory=0'); expect(result).not.toContain('status='); expect(result).not.toContain('description='); expect(result).not.toContain('emptyString='); }); it('should return base URL when all parameters are filtered out', () => { const result = testBuildUrl(hostResources, '/api/v2/hosts/', { status: undefined, description: null, emptyString: '' }); expect(result).toBe('/api/v2/hosts/'); expect(result).not.toContain('?'); }); }); }); //# sourceMappingURL=HostResources.test.js.map