Skip to content

Commit aa812d9

Browse files
authored
Create and publish binaries in CI (#44)
2 parents e084238 + e1ff4ae commit aa812d9

30 files changed

+300
-166
lines changed

.github/workflows/checks.yml

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,13 @@ env:
1010
jobs:
1111
build_and_test:
1212
name: Compilation
13-
runs-on: ubuntu-latest
13+
runs-on: ${{ matrix.os }}
1414
strategy:
1515
matrix:
16+
os:
17+
- ubuntu-latest
18+
- macos-latest
19+
- windows-latest
1620
toolchain:
1721
- stable
1822

@@ -27,7 +31,7 @@ jobs:
2731
uses: Swatinem/[email protected]
2832
with:
2933
cache-bin: "false"
30-
prefix-key: "v5-maho"
34+
prefix-key: "v5-maho-${{ matrix.os }}-${{ matrix.toolchain }}"
3135

3236
- name: Install cargo-binstall
3337
uses: cargo-bins/[email protected]
@@ -60,7 +64,7 @@ jobs:
6064
uses: Swatinem/[email protected]
6165
with:
6266
cache-bin: "false"
63-
prefix-key: "v4-maho"
67+
prefix-key: "v5-maho-${{ matrix.toolchain }}"
6468

6569
- name: Install cargo-binstall
6670
uses: cargo-bins/[email protected]

.github/workflows/release.yml

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
name: Cargo Build & Release
2+
3+
permissions:
4+
contents: write
5+
6+
on:
7+
push:
8+
tags:
9+
- v[0-9]+.*
10+
11+
jobs:
12+
create-release:
13+
runs-on: ubuntu-latest
14+
steps:
15+
- uses: actions/checkout@v4
16+
- uses: taiki-e/create-gh-release-action@v1
17+
with:
18+
token: ${{ secrets.GITHUB_TOKEN }}
19+
20+
build-and-release:
21+
needs: create-release
22+
name: Build & Release
23+
runs-on: ${{ matrix.os }}
24+
strategy:
25+
matrix:
26+
include:
27+
- os: ubuntu-latest
28+
target: x86_64-unknown-linux-gnu
29+
30+
- os: ubuntu-latest
31+
target: x86_64-unknown-linux-musl
32+
33+
- os: macos-latest
34+
target: x86_64-apple-darwin
35+
36+
- os: macos-latest
37+
target: aarch64-apple-darwin
38+
39+
- os: windows-latest
40+
target: x86_64-pc-windows-msvc
41+
42+
steps:
43+
- name: Checkout repository
44+
uses: actions/checkout@v4
45+
46+
- name: Install cross-compilation tools
47+
uses: taiki-e/setup-cross-toolchain-action@v1
48+
if: startsWith(matrix.os, 'ubuntu')
49+
with:
50+
target: ${{ matrix.target }}
51+
52+
- name: Build and Release
53+
uses: taiki-e/upload-rust-binary-action@v1
54+
with:
55+
bin: purescript-analyzer
56+
package: purescript-analyzer
57+
target: ${{ matrix.target }}
58+
token: ${{ secrets.GITHUB_TOKEN }}

Cargo.lock

Lines changed: 19 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

compiler-bin/Cargo.toml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,7 @@ tokio = { version = "1.46.1", features = ["full"] }
2222
tower = "0.5.2"
2323
tracing = "0.1.41"
2424
tracing-subscriber = "0.3.19"
25+
url = "2.5.7"
26+
27+
[target.'cfg(not(unix))'.dependencies]
28+
tokio-util = { version = "0.7.16", features = ["compat"] }

compiler-bin/src/lib.rs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,8 @@ fn initialized(state: &mut State, _: InitializedParams) -> ControlFlow<async_lsp
109109
if let Some(files) = files {
110110
tracing::info!("Loading {} files.", files.len());
111111
for file in &files {
112-
let uri = format!("file://{}", file.to_str().unwrap());
112+
let url = url::Url::from_file_path(file).unwrap();
113+
let uri = url.to_string();
113114
let text = fs::read_to_string(file).unwrap();
114115
on_change(state, &uri, &text);
115116
}
@@ -258,10 +259,17 @@ pub async fn analyzer_loop() {
258259
let subscriber = Registry::default().with(fmt).with(SpanTimingLayer);
259260
tracing::subscriber::set_global_default(subscriber).unwrap();
260261

262+
#[cfg(unix)]
261263
let (stdin, stdout) = (
262264
async_lsp::stdio::PipeStdin::lock_tokio().unwrap(),
263265
async_lsp::stdio::PipeStdout::lock_tokio().unwrap(),
264266
);
265267

266-
server.run_buffered(stdin, stdout).await.unwrap()
268+
#[cfg(not(unix))]
269+
let (stdin, stdout) = (
270+
tokio_util::compat::TokioAsyncReadCompatExt::compat(tokio::io::stdin()),
271+
tokio_util::compat::TokioAsyncWriteCompatExt::compat_write(tokio::io::stdout()),
272+
);
273+
274+
server.run_buffered(stdin, stdout).await.unwrap();
267275
}

compiler-core/building/src/prim.rs

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ use url::Url;
66

77
use crate::QueryEngine;
88

9-
pub const HOST: &str = "generated";
9+
pub const SCHEME: &str = "prim";
1010
pub const PRIM: &str = include_str!("prim/Prim.purs");
1111
pub const PRIM_BOOLEAN: &str = include_str!("prim/Prim.Boolean.purs");
1212
pub const PRIM_COERCE: &str = include_str!("prim/Prim.Coerce.purs");
@@ -29,7 +29,7 @@ pub fn configure(engine: &mut QueryEngine, files: &mut Files) {
2929
("Prim.Symbol", PRIM_SYMBOL),
3030
("Prim.TypeError", PRIM_TYPE_ERROR),
3131
] {
32-
let path = format!("file://{HOST}/{name}.purs");
32+
let path = format!("{SCHEME}://localhost/{name}.purs");
3333
let id = files.insert(path, content);
3434

3535
engine.set_content(id, content);
@@ -44,15 +44,12 @@ pub static TEMPORARY_DIRECTORY: LazyLock<TempDir> = LazyLock::new(|| {
4444
.expect("invariant violated: failed to create TEMPORARY_DIRECTORY")
4545
});
4646

47-
pub fn handle_generated(mut uri: Url, content: &str) -> Option<Url> {
48-
if uri.host_str() != Some(HOST) {
47+
pub fn handle_generated(uri: Url, content: &str) -> Option<Url> {
48+
if uri.scheme() != SCHEME {
4949
return Some(uri);
5050
}
5151

52-
uri.set_host(Some("localhost")).ok()?;
53-
let original = uri.to_file_path().ok()?;
54-
55-
let file = original.components().next_back()?;
52+
let file = uri.path_segments()?.next_back()?;
5653
let path = TEMPORARY_DIRECTORY.path().join(file);
5754

5855
let mut file = File::create(&path).ok()?;

compiler-core/indexing/tests/indexing.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,8 @@ use std::fmt::Write;
77
use syntax::cst;
88

99
fn index_source(source: &str) -> (cst::Module, FullIndexedModule) {
10-
let lexed = lexing::lex(source);
10+
let source = source.replace("\r\n", "\n").replace("\r", "\n");
11+
let lexed = lexing::lex(&source);
1112
let tokens = lexing::layout(&lexed);
1213

1314
let (parsed, _) = parsing::parse(&lexed, &tokens);

compiler-core/lexing/tests/lexer.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,8 @@ use test_each_file::test_each_file;
33
test_each_file! { in "./compiler-core/lexing/tests/lexer" => |content: &str| {
44
use std::fmt::Write;
55

6-
let lexed = lexing::lex(content);
6+
let content = content.replace("\r\n", "\n").replace("\r", "\n");
7+
let lexed = lexing::lex(&content);
78

89
let mut snapshot = String::new();
910
for index in 0..lexed.len() {

compiler-core/parsing/tests/parser.rs

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,23 +1,26 @@
11
use test_each_file::test_each_file;
22

33
test_each_file! { in "./compiler-core/parsing/tests/parser" => |content: &str| {
4-
let lexed = lexing::lex(content);
4+
let content = content.replace("\r\n", "\n").replace("\r", "\n");
5+
let lexed = lexing::lex(&content);
56
let tokens = lexing::layout(&lexed);
67
let (parsed, errors) = parsing::parse(&lexed, &tokens);
78
let node = parsed.syntax_node();
89
insta::assert_debug_snapshot!((node, errors));
910
}}
1011

1112
test_each_file! { in "./compiler-core/parsing/tests/parser" as lossless => |content: &str| {
12-
let lexed = lexing::lex(content);
13+
let content = content.replace("\r\n", "\n").replace("\r", "\n");
14+
let lexed = lexing::lex(&content);
1315
let tokens = lexing::layout(&lexed);
1416
let (parsed, _) = parsing::parse(&lexed, &tokens);
1517
let node = parsed.syntax_node();
1618
assert_eq!(node.to_string(), content);
1719
}}
1820

1921
test_each_file! { in "./compiler-core/parsing/tests/parser" as stability => |content: &str| {
20-
let lexed = lexing::lex(content);
22+
let content = content.replace("\r\n", "\n").replace("\r", "\n");
23+
let lexed = lexing::lex(&content);
2124
for index in 0..lexed.len() - 1 {
2225
let partial = lexed.text_in_range(0..index + 1);
2326
let lexed = lexing::lex(partial);

compiler-core/sugar/src/bracketing.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -237,21 +237,21 @@ pub fn bracketed(
237237
let mut binders = FxHashMap::default();
238238
for (id, kind) in lowered.intermediate.iter_binder() {
239239
if let BinderKind::OperatorChain { head, tail } = kind {
240-
binders.insert(id, bracket(external, &lowered, *head, tail));
240+
binders.insert(id, bracket(external, lowered, *head, tail));
241241
}
242242
}
243243

244244
let mut expressions = FxHashMap::default();
245245
for (id, kind) in lowered.intermediate.iter_expression() {
246246
if let ExpressionKind::OperatorChain { head, tail } = kind {
247-
expressions.insert(id, bracket(external, &lowered, *head, tail));
247+
expressions.insert(id, bracket(external, lowered, *head, tail));
248248
}
249249
}
250250

251251
let mut types = FxHashMap::default();
252252
for (id, kind) in lowered.intermediate.iter_type() {
253253
if let TypeKind::OperatorChain { head, tail } = kind {
254-
types.insert(id, bracket(external, &lowered, *head, tail));
254+
types.insert(id, bracket(external, lowered, *head, tail));
255255
}
256256
}
257257

0 commit comments

Comments
 (0)