mirror of
https://github.com/ollama/ollama.git
synced 2026-09-21 05:28:00 -05:00
* create: add server-side MLX imports and drop GGUF conversion Support safetensors imports through the MLX create pipeline both locally and on the server, including remote upload/staging, draft layer handling, cancellation propagation, transfer limits, and shared manifest/blob writing. Limit GGUF create to wrapping existing GGUF inputs into Ollama manifests. Remove the in-tree safetensors-to-GGUF converter, server quantization path, and converter-only dependencies so GGUF conversion and quantization stay in llama.cpp tooling. Keep the MLX path focused on supported safetensors model creation with validation before MLX work, and expose that flow without the --experimental CLI gate. * address comments * add client side gguf create fast path * address comments * rebase adjustments
176 lines
5.4 KiB
Go
176 lines
5.4 KiB
Go
package llm
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"runtime"
|
|
"slices"
|
|
"testing"
|
|
)
|
|
|
|
func TestLlamaCppBinaryCandidates(t *testing.T) {
|
|
root := t.TempDir()
|
|
|
|
tests := []struct {
|
|
name string
|
|
search llamaCppBinarySearch
|
|
want []string
|
|
wantFirst string
|
|
}{
|
|
{
|
|
name: "linux production layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "linux", "bin", "ollama"),
|
|
goos: "linux",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{filepath.Join(root, "linux", "lib", "ollama", "llama-server")},
|
|
wantFirst: filepath.Join(root, "linux", "lib", "ollama", "llama-server"),
|
|
},
|
|
{
|
|
name: "windows production layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "windows", "ollama.exe"),
|
|
goos: "windows",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{filepath.Join(root, "windows", "lib", "ollama", "llama-server.exe")},
|
|
wantFirst: filepath.Join(root, "windows", "lib", "ollama", "llama-server.exe"),
|
|
},
|
|
{
|
|
name: "darwin production layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "Ollama.app", "Contents", "Resources", "ollama"),
|
|
goos: "darwin",
|
|
goarch: "arm64",
|
|
},
|
|
want: []string{filepath.Join(root, "Ollama.app", "Contents", "Resources", "llama-server")},
|
|
wantFirst: filepath.Join(root, "Ollama.app", "Contents", "Resources", "llama-server"),
|
|
},
|
|
{
|
|
name: "darwin standard install layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "darwin", "bin", "ollama"),
|
|
goos: "darwin",
|
|
goarch: "arm64",
|
|
},
|
|
want: []string{filepath.Join(root, "darwin", "lib", "ollama", "llama-server")},
|
|
},
|
|
{
|
|
name: "windows standard install layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "windows", "bin", "ollama.exe"),
|
|
goos: "windows",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{filepath.Join(root, "windows", "lib", "ollama", "llama-server.exe")},
|
|
},
|
|
{
|
|
name: "local per-architecture dist layout",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "dist", "darwin-arm64", "ollama"),
|
|
goos: "darwin",
|
|
goarch: "arm64",
|
|
},
|
|
want: []string{filepath.Join(root, "dist", "darwin-arm64", "lib", "ollama", "llama-server")},
|
|
},
|
|
{
|
|
name: "local top-level executable on linux",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "ollama"),
|
|
workingDir: root,
|
|
goos: "linux",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{
|
|
filepath.Join(root, "build", "lib", "ollama", "llama-server"),
|
|
filepath.Join(root, "dist", "linux-amd64", "lib", "ollama", "llama-server"),
|
|
filepath.Join(root, "dist", "linux_amd64", "lib", "ollama", "llama-server"),
|
|
},
|
|
},
|
|
{
|
|
name: "local top-level executable on windows",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "ollama.exe"),
|
|
workingDir: root,
|
|
goos: "windows",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{
|
|
filepath.Join(root, "build", "lib", "ollama", "llama-server.exe"),
|
|
filepath.Join(root, "dist", "windows-amd64", "lib", "ollama", "llama-server.exe"),
|
|
},
|
|
},
|
|
{
|
|
name: "local top-level executable on darwin",
|
|
search: llamaCppBinarySearch{
|
|
executable: filepath.Join(root, "ollama"),
|
|
workingDir: root,
|
|
goos: "darwin",
|
|
goarch: "arm64",
|
|
},
|
|
want: []string{
|
|
filepath.Join(root, "build", "lib", "ollama", "llama-server"),
|
|
filepath.Join(root, "dist", "darwin-arm64", "lib", "ollama", "llama-server"),
|
|
filepath.Join(root, "dist", "darwin", "llama-server"),
|
|
},
|
|
},
|
|
{
|
|
name: "explicit lib path stays first",
|
|
search: llamaCppBinarySearch{
|
|
libOllamaPath: filepath.Join(root, "install", "lib", "ollama"),
|
|
executable: filepath.Join(root, "app", "ollama"),
|
|
workingDir: filepath.Join(root, "work"),
|
|
goos: "linux",
|
|
goarch: "amd64",
|
|
},
|
|
want: []string{filepath.Join(root, "install", "lib", "ollama", "llama-server")},
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
candidates := llamaCppBinaryCandidates("llama-server", tt.search)
|
|
if tt.wantFirst != "" && candidates[0] != tt.wantFirst {
|
|
t.Fatalf("first candidate = %q, want %q; all candidates: %v", candidates[0], tt.wantFirst, candidates)
|
|
}
|
|
if tt.search.libOllamaPath != "" && candidates[0] != tt.want[0] {
|
|
t.Fatalf("first candidate = %q, want %q; all candidates: %v", candidates[0], tt.want[0], candidates)
|
|
}
|
|
for _, want := range tt.want {
|
|
if !slices.Contains(candidates, want) {
|
|
t.Fatalf("missing candidate %q; all candidates: %v", want, candidates)
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestLlamaCppBinarySearchPrefersPlatformBuildOutput(t *testing.T) {
|
|
root := t.TempDir()
|
|
cpuDir := filepath.Join(root, "build", "llama-server-cpu", "bin")
|
|
cudaDir := filepath.Join(root, "build", "llama-server-cuda", "bin")
|
|
for _, dir := range []string{cpuDir, cudaDir} {
|
|
if err := os.MkdirAll(dir, 0o755); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
}
|
|
|
|
name := llamaCppBinaryName("llama-quantize", runtime.GOOS)
|
|
cpuBin := filepath.Join(cpuDir, name)
|
|
cudaBin := filepath.Join(cudaDir, name)
|
|
for _, path := range []string{cpuBin, cudaBin} {
|
|
if err := os.WriteFile(path, nil, 0o755); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
}
|
|
|
|
got, _, err := findLlamaCppBinary("llama-quantize", llamaCppBinarySearch{workingDir: root})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if got != cudaBin {
|
|
t.Fatalf("findLlamaCppBinary = %q, want %q", got, cudaBin)
|
|
}
|
|
}
|