-
Notifications
You must be signed in to change notification settings - Fork 363
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RFC: Target-project based control of TypescriptConfig
from TypeScriptProject
#3448
Comments
I am not a fan of abstracting away tsconfig to a third-party. Projen is the config manager. By moving away the responsibility of the config upstream, then each projen-based project is at risk of configuration shifting upstream. It breeds an action-at-a-distance type of problem. And When I have the full config locally, I can easily see at a glance what can be tweaked and/or what is wrongly configured. And when it's extending some other one, it's not that simple. You must lookup inside Or use |
@moltar Thats a fair assessment. I see what you're saying about trusting and relying on someone else. The '@tsconfig' configurations are really just an example of a curated set of configs for a variety of targets. There may even be others to choose from. I think providing our own set of curated options works as well, would in fact be ideal. I didn't want to suggest that burden necessarily be picked up by this project. If this project is accepting of that responsibility, then that's all the better. I'd say being able to choose is a very important part. Even if we choose to curate our own set of configurations, I think it would be in our best interest to allow choosing from outside options as well. I don't see it being a risk as long as it's for the application code. The only place I'd be uncomfortable with broad choice is for compiling and execution of |
I'm off the relatively strong opinion that |
Well, it's worth breaking it down with a few example scenarios I've encountered:
The 👍 indicates that we can use the same TS configuration for the application code as for The 👎 indicates that they cannot be shared since the targets are incompatible. In all 👎 cases and several 👍 cases, the Tests are tricky, as you want them to match the target environment, but you have to run them with the tooling of the project, so I think they have to fall under either the tooling config ( |
Which brings to mind something I haven't thought of (or heard of) before, which would be splitting the tsconfig settings into two (maybe more?) categories, and providing option groups of those categories that you mix and match. Categories such as strictness, style, and target. Not just considering it all just target. Conversationally, that would read something like: "We're going to make a react-ts project, the tsconfig settings will be the strictest-reasonable ( I realize that I'm less sure about this part, but if we're intending to curate settings groups, it would be good to at least separate "strictness rules" from "target rules". |
The actual reason here is that the tsconfig is used to discover files included in the jsii assembly and projen code should not be included. The config itself is perfectly capable of compiling projen code.
I'm not entirely sure I follow why this would prevent projen code from being run, but I can accept that there are cases where it's not desirable to share the config. 👍🏻 |
I though more about this and I'm not convinced we need to introduce a new concept of a "target". The core of the issue seems to be that currently I think we should take a step back and look at how we can model these properties while satisfying the following requirements:
I believe there is one more requirement that you can be distilled out from the conservations, but I'm not entirely sure yet about its value and if I understand the need correctly. It might also just be an extension of (3). So please @giseburt if you could assist to set this out correctly:
With the exception of (3) I believe these are already achievable with today's API, but super hacky. We are looking for a new API that can satisfy all the above requirements (once confirmed). We then also need to worry about migration, but let's make this a secondary concern. |
Good breakdown, @mrgrain. If we think in terms of L1, L2, L3 constructs based on those defined for CDK, briefly defined as:
One could argue that With that in mind, I believe the part I think this RFC is most concerned with is the creation of L3 constructs, including "apps" (
Pretty much, yes. Here's everything
I think we would want to keep everything as they are except the parts where the 🛠️ are. Going back to your list:
If
Actually, I think if we could amend values (IOW, set them after Specifically, if we put Sorry for the small novel. Footnotes
|
This is a good write up. I'll need some time to work through this. But a quick note aside: I'm not convinced the L1, L2, L3 terminology is very useful for projen. Even with the AWS CDK it kind of falls apart with the L2s. But for projen it's even worse: I don't have a better terminology at hand yet, just feel strongly that the Ls aren't cutting it. I also think it's important to differentiate strongly between Either way, it serves this discussion well enough, so I'm happy to go with this reasoning for now. |
I agree. The L terminology feels more marketing than tech. The main reason I left it in was to express the composability. There are L1s, which are the raw file containers, then logic above that, then ever-larger patterns of coordinating that logic and other patterns. Escape hatches reach past the logic and patterns to adjust the raw data, but also duplicating effort to have to know and understand the file layout, intent, etc that was otherwise handled. And that’s what was bugging me that I couldn’t get to directly but see now: not enough flexibility. I’m seeing this with the GitHub Workflows stuff too: too many things are set once at construction and can not be changed later, sometimes can’t even be read with reading the raw file data about to be written. To see the full value of composition and patterns, we need to be able to adjust intelligently beyond component construction. |
Yes and you are experiencing this because fundamentally the Construct Programming Model is build on the idea of correctness at construction time. Obviously we are way past this, but it has some nice properties as side effects. For example using a JSON RC file or passing values via the CLI. |
I think we can ease composition for those elements used primarily inside the patterns by exposing manipulation methods and maintain correctness at construction time, and I agree it is a slippery slope. For example, if we expose the ability to read and write More importantly we don’t lose the value of the understanding of how tsconfig and targets work that we’re providing by making adjustments have to happen via escape hatches. |
Two things:
|
Ok, I have made a PR that I think is a reasonable solution. I look forward to hearing feedback on this. I've been looking at it so long I worry I may have missed something important. Here's the solution in a nutshell: Phase 1:
Phase 2:
I have only four presets currently: export enum TypescriptConfigPresetsOptions {
PROJEN_CLASSIC = "PROJEN_CLASSIC",
NODE18 = "NODE18",
NODE20 = "NODE20",
STRICTEST = "STRICTEST",
}
The other presets are almost exactly copied from tsconfig/bases (I removed two psychotic values from "strictest"). I feel like there's a ton of room for evolution of these presets, especially since they can be combined. For example, would we want to make the Anyway, please take a look over in #3535 and let me know what you think. |
Problem: One of the many elements being managed by
TypeScriptProject
is theTypescriptConfig
, providing an opinionated defaultcompilerOptions
that are then expected to be overridden. TypeScript is used for a wider and wider range of projects, and the opinionatedcompilerOptions
only covers a static subset of those.We don't want to otherwise change how
TypeScriptProject
is managing theTypescriptConfig
, onlycompilerOptions
andextends
under certain circumstances.Those defaults cover a somewhat narrow target type (node app, basically), which I’m not complaining about, but is somewhat brittle and puts the maintenance burden on this project. Each project subtype (such as a React one) provides overrides, which is great, and this should make that easier as well.
I'm proposing to use the
@tsconfig
project maintained settings, choosing a base and optionally extending other sets like strictest while still allowing overrides.So, conversationally that would read as: “I’m building for Node20, would like the strictest settings, except
exactOptionalPropertyTypes
, which I find annoying and unhelpful.”Or, “I’m building for React in a browser, and then bundling it. I'll be using Node18 locally, and need my test code to be strict.”
That last one brings up the element of
tsconfig.dev.json
, which is for runningprojen
, local utilities that use typescript (eslint
,jest
/ts-jest
, etc.), and may have wildly different settings than the target intsconfig.json
. For this reason, we should also have the ability to say thattsconfig.dev.json
doesn't necessarily extend or even resembletsconfig.json
.Proposal: One possible way of doing this is via a
buildTarget
option inTypeScriptProjectOptions
, with enum values for the various targets, including@tsconfig
options:PROJEN_CLASSIC
(current defaults),NODE18
,NODE20
,REACT_NATIVE
, etc. For local tools (tsconfig.dev.conf
) perhapsrunTarget
would work, defaulting toPROJEN_CLASSIC
?Should also have the ability to add the
strictest
set. Maybe something likebuildTargetOptions: { strictest: true }
?Further, there should probably be an option for "full control" -
UNSPECIFIED
perhaps?With that in mind, the code for those conversations:
exactOptionalPropertyTypes
, which I find annoying and unhelpful.”Possible tasks:
compilerOptions
to be omitted (Tsconfig compilerOptions should be optional when extending another config. #3411)extends
and basecompilerOptions
PROJEN_CLASSIC
(unsure of name) is selected will the current defaults be applied@tsconfig
dependencies to thedevDeps
The text was updated successfully, but these errors were encountered: