Skip to content

Commit

Permalink
More tests
Browse files Browse the repository at this point in the history
  • Loading branch information
ngs committed Jan 20, 2017
1 parent 9f59132 commit 655b2e8
Show file tree
Hide file tree
Showing 9 changed files with 239 additions and 7 deletions.
1 change: 1 addition & 0 deletions .gitignore
@@ -1 +1,2 @@
chm2docset
_fixtures/Sample.docset/Contents/Resources/docSet.dsidx
1 change: 1 addition & 0 deletions README.md
Expand Up @@ -23,6 +23,7 @@ How to use

```sh
brew install chmlib
go get -u go github.com/ngs/chm2docset
go install github.com/ngs/chm2docset
chm2docset -platform docset-platform -out /path/to/MyRef.docset /path/to/MyReference.chm
```
Expand Down
11 changes: 11 additions & 0 deletions _fixtures/Sample.docset/Contents/Resources/Documents/sub/test4.htm
@@ -0,0 +1,11 @@
<html>
<head>
<title>test

4
</title>
</head>
<body>
test4
</body>
</html>
@@ -0,0 +1,9 @@
<html>
<head>
<title>test 1
</title>
</head>
<body>
test1
</body>
</html>
10 changes: 10 additions & 0 deletions _fixtures/Sample.docset/Contents/Resources/Documents/test2.htm
@@ -0,0 +1,10 @@
<html>
<head>
<title>test 2
yo
</title>
</head>
<body>
test2
</body>
</html>
@@ -0,0 +1,7 @@
<html>
<head>
</head>
<body>
test3
</body>
</html>
4 changes: 4 additions & 0 deletions _fixtures/bin/extract_chmLib
@@ -0,0 +1,4 @@
#!/bin/sh

[ -d tmp ] || mkdir tmp
echo $@ > tmp/fixtureinput.txt
22 changes: 16 additions & 6 deletions chm2docset.go
Expand Up @@ -16,6 +16,8 @@ import (
_ "github.com/mattn/go-sqlite3"
)

var logFatal = log.Fatal

func usage() {
fmt.Fprintf(os.Stderr, "usage: %s [inputfile]\n", os.Args[0])
flag.PrintDefaults()
Expand All @@ -24,7 +26,7 @@ func usage() {

func failOnError(err error) {
if err != nil {
log.Fatal(err)
logFatal(err)
}
}

Expand Down Expand Up @@ -128,26 +130,30 @@ func (opts *Options) PlistContent() string {

// WritePlist writes plist file
func (opts *Options) WritePlist() error {
return ioutil.WriteFile(opts.PlistPath(), []byte(opts.PlistContent()), 644)
return ioutil.WriteFile(opts.PlistPath(), []byte(opts.PlistContent()), 0644)
}

// Clean removes existing output
func (opts *Options) Clean() error {
return os.RemoveAll(opts.DocsetPath())
}

// CreateDirectory creates directory
func (opts *Options) CreateDirectory() error {
return os.MkdirAll(opts.ContentPath(), 0755)
}

// ExtractSource extracts source to destination
func (opts *Options) ExtractSource() error {
if err := os.MkdirAll(opts.ContentPath(), 0755); err != nil {
return err
}
cmd := exec.Command("extract_chmLib", opts.SourcePath, opts.ContentPath())
return cmd.Run()
}

// CreateDatabase creates database
func (opts *Options) CreateDatabase() error {
os.Remove(opts.DatabasePath())
titleRE := regexp.MustCompile("<title>([^<]+)</title>")
spacesRE := regexp.MustCompile("[\\s\\t]+")
db, err := sql.Open("sqlite3", opts.DatabasePath())
if err != nil {
return err
Expand Down Expand Up @@ -178,7 +184,10 @@ func (opts *Options) CreateDatabase() error {
content := string(b)
res := titleRE.FindAllStringSubmatch(content, -1)
if len(res) >= 1 && len(res[0]) >= 2 {
_, err := stmt.Exec(res[0][1], "Guide", strings.TrimPrefix(path, opts.ContentPath()))
ttl := strings.Replace(res[0][1], "\n", " ", -1)
ttl = spacesRE.ReplaceAllString(ttl, " ")
ttl = strings.TrimSpace(ttl)
_, err := stmt.Exec(ttl, "Guide", strings.TrimPrefix(path, opts.ContentPath()))
if err != nil {
return err
}
Expand All @@ -194,6 +203,7 @@ func (opts *Options) CreateDatabase() error {
func main() {
opts := NewOptions()
opts.Clean()
failOnError(opts.CreateDirectory())
failOnError(opts.ExtractSource())
failOnError(opts.CreateDatabase())
failOnError(opts.WritePlist())
Expand Down
181 changes: 180 additions & 1 deletion chm2docset_test.go
@@ -1,14 +1,22 @@
package main

import (
"database/sql"
"io"
"io/ioutil"
"log"
"os"
"reflect"
"testing"
)

func cleanTmp() {
os.RemoveAll("tmp")
}

type Test struct {
expected interface{}
actual interface{}
expected interface{}
}

func (test Test) Compare(t *testing.T) {
Expand All @@ -23,6 +31,89 @@ func (test Test) DeepEqual(t *testing.T) {
}
}

// Copies file source to destination dest.
func CopyFile(source string, dest string) (err error) {
sf, err := os.Open(source)
if err != nil {
return err
}
defer sf.Close()
df, err := os.Create(dest)
if err != nil {
return err
}
defer df.Close()
_, err = io.Copy(df, sf)
if err == nil {
if si, e := os.Stat(source); e != nil {
err = os.Chmod(dest, si.Mode())
}
}

return err
}

// Recursively copies a directory tree, attempting to preserve permissions.
// Source directory must exist, destination directory must *not* exist.
func CopyDir(source string, dest string) (err error) {

// get properties of source dir
fi, err := os.Stat(source)
if err != nil {
return err
}

if !fi.IsDir() {
return &CustomError{"Source is not a directory"}
}

// ensure dest dir does not already exist

_, err = os.Open(dest)
if !os.IsNotExist(err) {
return &CustomError{"Destination already exists"}
}

// create dest dir

err = os.MkdirAll(dest, fi.Mode())
if err != nil {
return err
}

entries, err := ioutil.ReadDir(source)

for _, entry := range entries {

sfp := source + "/" + entry.Name()
dfp := dest + "/" + entry.Name()
if entry.IsDir() {
err = CopyDir(sfp, dfp)
if err != nil {
log.Println(err)
}
} else {
// perform copy
err = CopyFile(sfp, dfp)
if err != nil {
log.Println(err)
}
}

}
return
}

// A struct for returning custom error messages
type CustomError struct {
What string
}

// Returns the error message defined in What as a string
func (e *CustomError) Error() string {
return e.What
}

func TestNewOptionsSourceUnspecified(t *testing.T) {
os.Args = []string{"chm2docset"}
opts := NewOptions()
Expand Down Expand Up @@ -125,3 +216,91 @@ func TestPlistContent(t *testing.T) {
</dict>
</plist>`}.Compare(t)
}

func TestWritePlist(t *testing.T) {
opts := &Options{
SourcePath: "/foo/bar/baz.chm",
Outdir: "tmp/foo.docset",
}
opts.CreateDirectory()
err := opts.WritePlist()
if err != nil {
t.Errorf("Expected nil but got %v", err)
}
b, err := ioutil.ReadFile("tmp/foo.docset/Contents/Info.plist")
if err != nil {
t.Errorf("Expected nil but got %v", err)
}
Test{string(b), `<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>dashIndexFilePath</key>
<string>Welcome.htm</string>
<key>CFBundleIdentifier</key>
<string>io.ngs.documentation.baz</string>
<key>CFBundleName</key>
<string>baz</string>
<key>DocSetPlatformFamily</key>
<string></string>
<key>isDashDocset</key>
<true/>
</dict>
</plist>`}.Compare(t)
opts.Clean()
if stat, err := os.Stat("tmp/foo.docset"); os.IsExist(err) {
t.Errorf("Expect not exist but exists %v", stat)
}
cleanTmp()
}

func TestExtractSource(t *testing.T) {
opts := &Options{
SourcePath: "/foo/bar/baz.chm",
Outdir: "tmp/foo.docset",
}
opts.CreateDirectory()
os.Setenv("PATH", "_fixtures/bin:"+os.Getenv("PATH"))
err := opts.ExtractSource()
if err != nil {
t.Errorf("Expected nil but got %v", err)
}
b, err := ioutil.ReadFile("tmp/fixtureinput.txt")
if err != nil {
t.Errorf("Expected nil but got %v", err)
}
Test{string(b), "/foo/bar/baz.chm tmp/foo.docset/Contents/Resources/Documents\n"}.Compare(t)
cleanTmp()
}

func TestCreateDatabase(t *testing.T) {
opts := &Options{
SourcePath: "/foo/bar/baz.chm",
Outdir: "tmp/Sample.docset",
}
opts.Clean()
CopyDir("_fixtures/Sample.docset", "tmp/Sample.docset")
opts.CreateDatabase()
db, _ := sql.Open("sqlite3", opts.DatabasePath())
rows, _ := db.Query("SELECT * FROM searchIndex")
columns, _ := rows.Columns()
Test{columns, []string{"id", "name", "type", "path"}}.DeepEqual(t)
grid := [][]string{}
for rows.Next() {
var id string
var name string
var indexType string
var path string
err := rows.Scan(&id, &name, &indexType, &path)
if err != nil {
t.Errorf("Got errror %v", err)
}
grid = append(grid, []string{id, name, indexType, path})
}
Test{grid, [][]string{
{"1", "test 4", "Guide", "/sub/test4.htm"},
{"2", "test 1", "Guide", "/test1.htm"},
{"3", "test 2 yo", "Guide", "/test2.htm"},
}}.DeepEqual(t)
cleanTmp()
}

0 comments on commit 655b2e8

Please sign in to comment.