Say I have a module storage-abstract
, which contains abstract logic (framework) for storing key/values. I also have some (arbitrarily many) implementations of this abstraction, each in a separate module, like storage-files
, storage-db
, storage-cloud
and so on.
Now say that there is a class AbstractStorage
in storage-abstract
that looks like follows:
// in storage-abstract
import {Interval} from 'some-3rd-party-lib';
abstract class AbstractStorage {
// ...
protected abstract _storageLimit: Interval;
}
export {AbstractStorage}
Now each concrete storage has to provide its own value for _storageLimit
and thus know Interval
. I could solve this the following way:
// in storage-files
import {AbstractStorage} from 'storage-abstract';
import {Interval} from 'some-3rd-party-lib';
class FilesStorage extends AbstractStorage {
// ...
protected _storageLimit = new Interval(1, 7);
}
export {FilesStorage}
This works fine, but the problem is that now storage-abstract
and storage-files
may depend on different versions of some-3rd-party-lib
, causing subtle bugs somewhere. The approach to prevent this (at least for NPM) is to specify some-3rd-party-lib
as a peer dependency (with a certain version) of storage-abstract
I assume.
But there is another approach: Given that storage-abstract
is in some sense like an API to storage-files
, it may (re-)export Interval
; storage-files
may then use this export and thus no longer depend on some-3rd-party-lib
directly (or its own version of it):
// in storage-abstract
// ...
export {
AbstractStorage,
Interval, // <-- new
}
// in storage-files
import {
AbstractStorage,
Interval, // <-- new
} from 'storage-abstract';
// removed: import {Interval} from 'some-3rd-party-lib';
// ...
Which approach is the better (or what are advantages and disadvantages)?