diff --git a/core/index.ts b/core/index.ts
new file mode 100644
index 0000000..ecdfd6a
--- /dev/null
+++ b/core/index.ts
@@ -0,0 +1,9 @@
+export type {
+ Observable,
+ Observer,
+ Subscription,
+ RatyStore,
+ RatyStoreOptions,
+} from "./store"
+export { create } from "./store"
+export * as Raty from './store'
\ No newline at end of file
diff --git a/core/store.ts b/core/store.ts
new file mode 100644
index 0000000..4b16d98
--- /dev/null
+++ b/core/store.ts
@@ -0,0 +1,64 @@
+export interface Observable {
+ subscribe(observer: Observer): Subscription
+}
+
+export interface Observer {
+ (value: A): void
+}
+
+export interface Subscription {
+ unsubscribe(): void
+}
+
+export interface RatyStore extends Observable {
+ get(): number
+ set(value: number): void
+ set(modifier: ()=> number): void
+ cancel(): void
+}
+
+export interface RatyStoreOptions {
+ value: (() => number) | number
+}
+
+export function create(options: RatyStoreOptions): RatyStore {
+ const initialValue = typeof options.value === 'function' ? options.value() : options.value
+ let value = initialValue
+
+ const listeners = new Set>()
+
+ const notify = () => {
+ for (const listener of listeners) {
+ listener(value)
+ }
+ }
+
+ const set = (fa: (() => number) | number) => {
+ const newValue = typeof fa === 'function' ? fa() : value
+
+ if (newValue !== value) {
+ value = newValue
+
+ notify()
+ }
+ }
+
+ const get = () => value
+
+ const subscribe = (observer: Observer): Subscription => {
+ listeners.add(observer)
+
+ return {
+ unsubscribe: () => listeners.delete(observer)
+ }
+ }
+
+ const cancel = () => set(initialValue)
+
+ return {
+ get,
+ set,
+ subscribe,
+ cancel,
+ }
+}
\ No newline at end of file