UNPKG

@datametria/vue-components

Version:

DATAMETRIA Vue.js 3 Component Library with Multi-Brand Theming - 51 components + 10 composables with theming support, WCAG 2.2 AA, dark mode, responsive system

147 lines (127 loc) 3.76 kB
/** * useTheme Composable Tests * @author Vander Loto - CTO DATAMETRIA * @date 13/11/2025 */ import { describe, it, expect } from 'vitest' import { mount } from '@vue/test-utils' import { h } from 'vue' import ThemeProvider from '../ThemeProvider.vue' import { useTheme } from '../useTheme' import { defaultTokens } from '../tokens' import type { Theme } from '../types' const testTheme: Theme = { name: 'Test Theme', tokens: defaultTokens } describe('useTheme', () => { it('should throw error when used outside ThemeProvider', () => { // Suprimir warnings do Vue durante este teste const originalWarn = console.warn console.warn = () => {} expect(() => { const TestComponent = { setup() { useTheme() return () => h('div', 'Test') } } mount(TestComponent) }).toThrow('useTheme must be used within a ThemeProvider') // Restaurar console.warn console.warn = originalWarn }) it('should return theme when used inside ThemeProvider', () => { const TestComponent = { setup() { const theme = useTheme() expect(theme).toBeDefined() expect(theme.value.name).toBe('Test Theme') return () => h('div', theme.value.name) } } const wrapper = mount(ThemeProvider, { props: { theme: testTheme }, slots: { default: h(TestComponent) } }) expect(wrapper.text()).toContain('Test Theme') }) it('should return theme tokens', () => { const TestComponent = { setup() { const theme = useTheme() expect(theme.value.tokens).toBeDefined() expect(theme.value.tokens.colors.primary).toBe('#0072CE') return () => h('div', 'Test') } } mount(ThemeProvider, { props: { theme: testTheme }, slots: { default: h(TestComponent) } }) }) it('should access all token categories', () => { const TestComponent = { setup() { const theme = useTheme() expect(theme.value.tokens.colors).toBeDefined() expect(theme.value.tokens.typography).toBeDefined() expect(theme.value.tokens.spacing).toBeDefined() expect(theme.value.tokens.radius).toBeDefined() expect(theme.value.tokens.shadows).toBeDefined() expect(theme.value.tokens.transitions).toBeDefined() return () => h('div', 'Test') } } mount(ThemeProvider, { props: { theme: testTheme }, slots: { default: h(TestComponent) } }) }) it('should work in nested components', () => { const GrandchildComponent = { setup() { const theme = useTheme() return () => h('div', { class: 'grandchild' }, theme.value.name) } } const ChildComponent = { setup() { return () => h('div', { class: 'child' }, h(GrandchildComponent)) } } const wrapper = mount(ThemeProvider, { props: { theme: testTheme }, slots: { default: h(ChildComponent) } }) expect(wrapper.find('.grandchild').text()).toContain('Test Theme') }) it('should provide helpful error message', () => { // Suprimir warnings do Vue durante este teste const originalWarn = console.warn console.warn = () => {} try { const TestComponent = { setup() { useTheme() return () => h('div', 'Test') } } mount(TestComponent) } catch (error) { expect(error).toBeInstanceOf(Error) expect((error as Error).message).toContain('ThemeProvider') expect((error as Error).message).toContain('Wrap your component tree') } // Restaurar console.warn console.warn = originalWarn }) })