Giter Club home page Giter Club logo

lf's Introduction

LF

Google Groups | Doc | Wiki | #lf (on Libera.Chat) | #lf:matrix.org (with IRC bridge)

Go Build Go Report Card

lf (as in "list files") is a terminal file manager written in Go with a heavy inspiration from ranger file manager. See faq for more information and tutorial for a gentle introduction with screencasts.

multicol-screenshot singlecol-screenshot

Features

  • Cross-platform (Linux, macOS, BSDs, Windows)
  • Single binary without any runtime dependencies
  • Fast startup and low memory footprint due to native code and static binaries
  • Asynchronous IO operations to avoid UI locking
  • Server/client architecture and remote commands to manage multiple instances
  • Extendable and configurable with shell commands
  • Customizable keybindings (vi and readline defaults)
  • A reasonable set of other features (see the documentation)

Non-Features

  • Tabs or windows (better handled by window manager or terminal multiplexer)
  • Builtin pager/editor (better handled by your pager/editor of choice)
  • Builtin commands for file operations (better handled by the underlying shell tools including but not limited to mkdir, touch, chmod, chown, chgrp, and ln)

Installation

See packages for community maintained packages.

See releases for pre-built binaries.

Building from the source requires Go.

On Unix:

env CGO_ENABLED=0 go install -ldflags="-s -w" github.com/gokcehan/lf@latest

On Windows cmd:

set CGO_ENABLED=0
go install -ldflags="-s -w" github.com/gokcehan/lf@latest

On Windows powershell:

$env:CGO_ENABLED = '0'
go install -ldflags="-s -w" github.com/gokcehan/lf@latest

Usage

After the installation lf command should start the application in the current directory.

Run lf -help to see command line options.

Run lf -doc to see the documentation.

See etc directory to integrate lf to your shell and/or editor. Example configuration files along with example colors and icons files can also be found in this directory.

See integrations to integrate lf to other tools.

See tips for more examples.

Contributing

See contributing for guidelines.

lf's People

Contributors

ath3 avatar catalyn45 avatar dependabot[bot] avatar doronbehar avatar gokcehan avatar gotroyb127 avatar horriblename avatar ilyagr avatar joelim-work avatar jurismajors avatar kenjitakahashi avatar kmarius avatar kmwenja avatar laktak avatar limero avatar michael-gallo avatar mtoohey31 avatar neeshy avatar occivink avatar p-ouellette avatar postsolar avatar provessor avatar raslop avatar rrveex avatar seekingblues avatar seerlite avatar sitiom avatar spfabgerman avatar valoq avatar vbauerster avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

lf's Issues

Show full path (including file name) on the first line

Currently if one wants to easily copy the full canonical path to the selected file, one has to copy the path from first line, then somehow show the full filename (often it's cut because of a too narrow column, so one needs to use e.g. some key binding running ls on the file) and then concatenate these two.

I'd like the selected file name being shown after the path on the first line to form a full canonical path to the selected file/dir as it's done in ranger.

Cursors behaviour

What the heck are cursor keys currently doing? It looks like this (I've kept pushing the up key, but it seems the same for all cursors):

out2

I guess I'd expect them to work like hjkl.

Make search cyclic?

I.e. go back to top with next n, after reaching bottom. That's how it usually works (in vim, ranger, etc.).

Segfault in readExpr

Happened to me several times right after starting lf, then disappeared some time later... I think it might have been caused by a leftover socket created with older version (before the async stuff started) of lf, but I'm not sure.

panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x20 pc=0x7dfc1]

goroutine 9 [running]:
panic(0x16c660, 0xc42000c0d0)
       	/usr/local/Cellar/go/1.7.1/libexec/src/runtime/panic.go:500 +0x1a1
fmt.Fprintln(0x0, 0x0, 0xc420029ee8, 0x1, 0x1, 0x0, 0x0, 0x0)
       	/usr/local/Cellar/go/1.7.1/libexec/src/fmt/print.go:248 +0x61
main.readExpr.func1(0x0, 0x0, 0xc42006eba0)
       	/Users/kenji/languages/.go/src/github.com/gokcehan/lf/client.go:64 +0xff
created by main.readExpr
       	/Users/kenji/languages/.go/src/github.com/gokcehan/lf/client.go:76 +0x71

That's more of a side note, but one thing we can certainly do is check client.go:64 for errors (yes, fmt functions return errors, but people always forget about it ;-)).

Display number of items inside directory instead of size

I'd like to have info displaying size for files, but number of items for directories (ranger style). It just feels more useful to me.
Having a setting like set showinfo dir-len-file-size sounds silly, but that's basically what I want.

Freeze when spamming a digit key

Hi,

lf completely freezes when I hit any numbered key (to use a command count for example) a few times (around 5 or more).

HTH.

`timefmt` is incorrectly parsed if containing spaces

Not sure when it was introduced, because I used a different time string until now, but the following statement in lfrc produces an error command not found: -0700:

set timefmt "2006-01-02 15:04:05.000000000 -0700"

While this works:

set timefmt "2006-01-02^15:04:05.000000000^-0700"

Don't use SHELL env var by default

Hi,

I think it might be better to just use /bin/sh (or whatever portable alternative) by default instead of $SHELL. Indeed, not all shells are posix-compliant (in particular fish, which I use) and quite a few things are broken as a result, which may be surprising to new users.

It should of course still be possible to override the shell with a setting in lfrc.

Drop into shell

The #6 got me thinking that this is what I use in ranger quite often. It has a Shift+s key that opens a new shell in the current dir. Would be nice to have :-).

Win.printr is called too much

It certainly gets called on quit and I think also on command completion. When you happen to be siting on a 25M SQL file with "not clever" previewer turned on, it takes lf ~5 seconds to unfreeze, which is kinda annoying.

Make `put` command configurable

I'd like to mimic the behavior of ranger in case a file with same name as the file being pasted exists. I.e. to rename the yanked file (even repeatedly) and then paste it.

It sounds like everybody could want to have a different behavior, so I'm proposing making the "paste" command configurable in the same way as the "open-file" command is (i.e. using cmd open-file ...).

On symlinks handling

Currently symlinks are handled as they are (i.e. files) and only checked when trying to list the items inside/cd to them.
I think it will be better to treat them transparently by handling their destination instead. This should simplify the logic and also have nice properties to the user, like having symlinks that point at dirs sorted among dirs, instead of files. But we'd still like to know they're symlinks, so that information can be displayed to the user as well.
This will obviously require taking both Lstat and Stat properties of the items. The performance should not be a problem, because we can avoid one redundant Sort inside ReadDir on the way, which pretty much evens out the speed.

Now, I've looked through lf code and also ranger code and I see two ways of doing this.

  1. The ranger way, store both Lstat and Stat outputs. I think this is not necessary, as the Lstat part is only ever used to check if a file is symlink or not. This can also lead to further fragmentation of the code (more on it below).
  2. Derive our own structure for file metadata, which will hold FileInfo + symlink flag [+ possibly something else, if needed]. This will be a bit more work, but looks cleaner to me. Plus, it will probably allow concatenating current currFile, currPath, etc. methods into one, instead of introducing another one. And it gives a better room for expansion, as required.

I am willing to do this, but I'd like to know what is your opinion on this first, @gokcehan.

`open-file` stack overflow

The macOS has unfortunate default opener named open, so I've tried

cmd open-file open $fx

which made lf crash and burn, because it tried to call it's own open cmd. Of course, it can be fixed by using $open instead, but perhaps we'd like to detect such cases and not die so hard.

(Re)map prefixes

I'd like to be able to do

map ; :

since it's mapped like this in ranger and I'm too used to not having to press Shift :-).
Personally, I'm fine with just hardcoding ; as alias for :, but maybe a more generic solution would be nice?

Cannot map to keys starting with one of the default

Which means, for example, that this doesn't work.

map dD trash

And it is copy/pasted from the tutorial :-).

I'd add that this makes sense that when some command is mapped to d, there would be no reasonable way to map d<sth>. Perhaps need a way to "unmap" the defaults?

Implement asynchronous event loop and remote commands

I have tried to do this 3 or 4 times before but gave up midway since things were getting too complicated but I think this is the only way forward so I'm pushing this. With commits 1e0b558 and 2f57496 main event loop in App.handleInp now works asynchronously. This is the beginning of implementing remote commands sent directly from the server.

I will try to elaborate the rationale a little bit.

  1. Currently yanked/deleted items are not shown in the ui which can get confusing (mentioned in #13). Some measures have already been taken for this problem but if we want to get the ui involved we need a way to notify all clients of changes.
  2. Currently there is no way to change the internals in a custom command. This works for most cases but sometimes it becomes limiting. For example it would be nice to be able to display a message for some commands (e.g. when the new filename exists in rename command example). This way we can truly say lf is scriptable in a language independent way.
  3. Currently there are no conditionals in the evaluator. Remote commands can be used as a workaround for this without inventing a new syntax for control flow.
  4. There are currently some subtle ui glitches (e.g. resize window while reading command in a prompt). This is still not fixed but asynchronous events may be useful for this purpose.
  5. Asynchronous event loop should help implement non-blocking file copying.
  6. Asynchronous event loop should help implement non-blocking file previewing (mentioned in #5).
  7. It should now be very straightforward to implement periodic renews. I am not a fan of this myself but I would accept a PR for this with a sensible default in case someone gets interested. I guess I should remove it from non-features section in the readme.
  8. It should make hacking lf much more fun with imaginative ways :)

First aim is to make a functional and stable implementation. I am not too happy with the type switch creeping in the codebase and directly passing App in UI.readExpr but the way prompting works make these necessary for now. Currently there is only a ping command implemented for testing. It can be used with OpenBSD netcat as follows:

echo "ping" | nc -U /tmp/lf.${USER}.sock

A send command is the next step to send arbitrary commands. This command may take an optional client id to send the command to that client only. We can pass current client id as an exported varible (e.g. $id) for use in custom commands. Maybe this id can also be used to seperate log files of each client.

Use colors from $LS_COLORS env variable

$LS_COLORS is used by ls to change the colors of some file types (e.g. image, archive) based on their extensions. This variable is usually set by dircolors which is configurable with a file. This command usually already exists in default ~/.bashrc files. It would be nice if lf also respects $LS_COLORS variable so users can have a way to customize some colors and use their existing configuration if any.

It is ok to take this and work on it if anyone is interested.

debug2: channel 0: window 997484 sent adjust 51092

Using a 64 bit linux binary from your downloads page on alpine over ssh I receive this error message on the line where my cursor is. This only happens in my ssh terminal (cmder). On the primary machine it works fine except --

Navigating to /proc and cursoring all the way to the bottom, lf freezes on both the real machine and the ssh terminal. q does not work to quit when this happens.

Visualize progress of potentially longer operations

Currently lf does not show any feedback for pasting a copy or similar operations. This gets frustrating especially in situations when the files/directories are on a remote storage or any other less reliable storage (USB flash drives, etc.) and one doesn't know whether the operation progresses normally or not.

E.g. copying even a small files takes time which freezes lf and the user does not know what's the reason (it might be a timed-out connection of the remote drive, it might be just a big file, it might be lf getting stuck because of bug, etc.).

Could you please add some progress indication (either something like a very simple "modal" dialog in the form of a red progress bar overlapping the status bar and showing percentage or even a job queue view independent from the main process)?

Format the filesize in status bar at the bottom

Currently the file size in status bar at the bottom is aligned left and always converted to the "shortest" human readable unit with an unspecified precision. I'd like to have the format either configurable or hard coded, but fulfill the following criteria.

  1. Align the precision separator at a position, that will allow displaying even the biggest files (which is not an issue because of the human readable units).

  2. Show always the precision separator and 3 significant digits after the precision separator.

  3. At the very end, there should be the human readable unit as it's now.

The reason for this is, that currently it feels like flickering when one wants to "sweep" the files to get an overview of their sizes or read any other part of the "status bar" (because it jumps back and forth while changing the focus of files).

Example status bar content for few consecutive files:

-rw------- dumblob dumblob 241.000B 2013-09-11 10:05:20.764016588 +0200
-rw-rw---- dumblob dumblob   2.500K 2016-05-15 19:52:47.304426855 +0200
-rwxr-x--- dumblob dumblob  10.000B 2016-10-13 15:01:18.326869789 +0200
-rw------- dumblob dumblob  12.045M 2016-10-06 16:27:19.233504938 +0200
-rw-rw---- dumblob dumblob   7.603T 2010-08-09 12:10:08.000000000 +0200
-rw------- dumblob dumblob   1.109P 2015-07-16 16:59:31.361387285 +0200
lrwxrwxrwx dumblob dumblob   8.000K 2012-07-22 19:24:55.302401623 +0200

Panic when starting up lf in directory with single directory symlink.

Hope the title is not confusing.

More precisely, given a directory structure like so:

$ pwd 
/home/occivink/tmp
$ tree
.
├── bar/
└── foo/
    └── bar -> /home/occivink/tmp/bar/

3 directories, 0 files

Trying to start lf lf in the directory foo will cause a panic on startup

gh doesn't "go home"

There might be a bug -- when I type gh lf appends my home directory to the current directory and thus doesn't go home.

Option to remove dead sessions from /tmp

Hi,

Sometimes some lf.${USER}.… files remain in /tmp, after a crash for example. It'd be convenient to have a way of letting lf remove them automatically, using a CLI flag for example (lf -prune or lf -clear).

Thanks.

handle symlinks

Currently you can't seem to chdir into a symlink, it tries to open it as a binary file. For me it meant it loaded it in firefox.

Make Ctrl+f and Ctrl+b to behave like in Vim

Currently C+f and C+b jump in a way, that they

  1. move the cursor already in the first jump unlike Vim, which doesn't move the cursor at all except for the last jump (when there is no other possibility to scroll the whole page while leaving the cursor at the same place)
  2. skip the whole screen, which
    1. in case of the first jump "flicker" (because the view moves always by one line)
    2. leaves no context like at least 2 lines (think of it as a counterpart of scrolloff)

I'd like to have the same behavior as in Vim - i.e. C+f and C+b would scroll the length of the screen minus the value of jumpoff (a non-negative integer number) without moving the cursor (the cursor would be moved first at the very end/beginning of the file list if requested to scroll "off" the file list).

`showinfo` should be able to handle multiple values

Currently showinfo is only able to display a single type of information (e.g. time or size). This can be limiting for wide screens and I don't see any reason why there should not be a way to display multiple types of information at the same time. We are already using : as separator for ratios option so I think we can use it here as well (e.g. set showinfo size:time).

It is ok to take this and work on it. There might be some details that should be discussed.

Russian chars mess up formatting

Like on screenshot. Had to cut a piece as there are some things I can't show, but should be visible what I mean.
screen shot 2016-10-16 at 19 58 26

May be related to #30. Perhaps termbox is thinking some of these chars are escape seqs or sth?

Broken preview pane escape code handling

The highlight -O ansi command correctly colors the preview pane text. However img2txt -f ansi and also elinks -dump 1 -dump-color-mode 1 both print the escape codes to the screen instead of displaying the colored output.

I believe the problem was introduced in commit 217d89f
The previous commit works fine for me.

Use the '\0' character as file name delimiter in $fx

I'm having huge issues with any delimiter other than '\0', because I work with many weirdly named files. Currently the $fx variable contains file names separated by ':', which I can't unfortunately use. Could you please add a set option to use '\0' instead of ':' in $fx?

Option for case-insensitive search

Currently the search is a perfect match (thus also case sensitive). I'd like to have an option to switch case insensitive matching on or even the "combination" of case (in)sensitive matching - i.e. when the searched term contains at least one upper letter, do a case sensitive search and in other cases do a case insensitive match (I use this "combined" matching all the time in vim).

Hm, thinking about search functionality improvements, maybe support for wildcards * and ? or even a fuzzy match (but this would require an external library for nearly no benefit) or at least support for "multi partial match" search (i.e. split the searched string by [[:blank:]]+ into words and then try to find the first word in the text, if found, start searching for the second word from the position of the character right behind the last character of the first match, if found, start searching for the third word from the position of the character right behind the last character of the second match, etc. - in other words a wildcard matching *word1*word2*word3*) would be very handy (regexes are too precise and not so concise).

Any comments on these suggestions? Of course, the exact behaviors should be then described in lf -doc.

As you type find command

Hi,

I'd like to be able to have lf jump automatically to a file (or enter the directory) if the contents of the search prompt matches a unique entry, unambiguously.

Thanks.

panic when pressing 'space' in empty direcotry

panic: runtime error: index out of range

goroutine 1 [running]:
panic(0x182290, 0x1050c030)
/usr/lib/go/src/runtime/panic.go:500 +0x33c
main.(_Nav).currPath(0x105697a0, 0x0, 0x0)
/home/alarm/dev/go/src/github.com/gokcehan/lf/nav.go:427 +0x70
main.(_Nav).toggle(0x105697a0)
/home/alarm/dev/go/src/github.com/gokcehan/lf/nav.go:347 +0x1c
main.(_CallExpr).eval(0x10568fc0, 0x1056e3b8, 0x0, 0x0, 0x0)
/home/alarm/dev/go/src/github.com/gokcehan/lf/eval.go:282 +0x21d4
main.(_App).handleInp(0x1056e3b8)
/home/alarm/dev/go/src/github.com/gokcehan/lf/app.go:69 +0x310
main.client()
/home/alarm/dev/go/src/github.com/gokcehan/lf/client.go:57 +0x54c
main.main()
/home/alarm/dev/go/src/github.com/gokcehan/lf/main.go:101 +0x440

Unicode Support

Could you use go-runewidth instead of golang.org/x/text/width ?
It is already used in termbox-go.
In addition, go-runewidth looks to provide better support in some cases.

Screen Captures
commit: 880615d
bad-case01

using go-runewidth
good-case01

patch is here:

diff --git a/ui.go b/ui.go
index 32d5e1e..7609437 100644
--- a/ui.go
+++ b/ui.go
@@ -17,6 +17,7 @@ import (
    "unicode"
    "unicode/utf8"

+   "github.com/mattn/go-runewidth"
    "github.com/nsf/termbox-go"
 )

@@ -203,7 +204,7 @@ func (win *Win) print(x, y int, fg, bg termbox.Attribute, s string) {
        if r == '\t' {
            x += gOpts.tabstop - (x-off)%gOpts.tabstop
        } else {
-           x += runeWidth(r)
+           x += runewidth.RuneWidth(r)
        }
    }
 }
@@ -272,11 +273,13 @@ func (win *Win) printd(dir *Dir, marks map[string]bool) {
            s = append(s, r)
        }

-       w := runeSliceWidth(s)
-       if w > win.w-2 {
-           s = runeSliceWidthRange(s, 0, win.w-2)
-       } else {
-           s = append(s, make([]rune, win.w-2-w)...)
+       if runewidth.StringWidth(string(s)) > win.w-2 {
+           for runewidth.StringWidth(string(s)) > win.w-2 {
+               s = s[:len(s)-1]
+           }
+       }
+       if runewidth.StringWidth(string(s)) < win.w-2 {
+           s = append(s, make([]rune, win.w-2-runewidth.StringWidth(string(s)))...)
        }

        switch gOpts.showinfo {

Symbolic link previews

When there the cursor is over a symbolic link to a directory, the preview pane does not display the correct contents, however descending into that directory is fine.

Implement forward and backward searching

Currently lf handles search and search-back commands along with their default keybinds but they are not actually implemented. An implementation should find the first match of the pattern and also provide commands to find next/prev matches (e.g. search-next and search-prev). These should ideally have default keybinds as well (e.g. n and N). For this purpose we need to save the last search pattern somewhere, most likely in a field in Nav.

This should not be very challenging. It is ok to take this and work on it.

Remember last visited paths over (server) restarts

One of the killer features of ranger, lf and similar file managers is, that they remember the selected file/dir after leaving dirs (i.e. going up in the file system tree hierarchy) and then when opening these dirs, they preselect the last selected file/dir.

Unfortunately this feature is not persistent over restarts, which makes it way less useful as one usually alternates between shell and lf while working.

In lf there are 2 "levels of persistence" to consider.

  1. Save this history server-side (i.e. all running clients will immediately send each record upon any change to lf server) for each client in it's own bucket. All history buckets will be merged (in case of a conflict the most recent record wins) to a "common" history and this then sent automatically to all newly opened lf clients and on-demand/manually to already running clients.

  2. Save the history buckets from 1. to a disk to allow persistency over lf server restarts (very convenient for unexpected logouts, crashes, etc.).

Technically are both points slightly inspired by some ideas used for ShaDa (Shared Data) from the Neovim project.

Highlighting code

Is it possible to use the highlight program to highlight go code when you display it? This would be a really cool enhancement since most users are gophers.

Sorry for the request when it's not really an issue. Regardless, I'm addicted to "lf" already -- great work!

Wrong preview when current selection is a directory symlink.

I swear I don't have that many symlinks.

Anyway, when the current selection is on a directory symlink, it will display in the preview pane the content of the last previewed directory.

Example:

$ tree
.
├── bar/
│   ├── bar1
│   ├── bar2
│   └── bar3
├── foo/
│   ├── foo1
│   ├── foo2
│   └── foo3
└── zab -> /home/occivink/tmp/bar/

If you start lf in such a directory and press down twice, it will show

foo1
foo2
foo3

in the preview pane. If you then go left and right, it will show

bar
foo
zab

You get the idea.

Expose the command count to the commands

Hi,

It'd be convenient to have the command count passed as an environment variable to the commands, like ${count}.

Example:

cmd foo ${{
printenv count # prints 2
}}
push 2:foo<ret>

Thanks.

Leave the cursor on the current file

Currently, LF is keeping the cursor on the bottom of the screen.
I'm using a screen reader, and moving the selection will just read the bottom line containing the file permissions.
Could the cursor move to the line containing the selected file?

Tagging an entry doesn't update the rightmost panel

Hi,

Upon marking an entry, the cursor jumps to the next entry in the main column, and the panel on the right isn't updated when the entry is a directory (it's supposed to list the files in the directory, which right after the one that was marked).

Thanks.

How to delete a file?

Hey,

It's not clear how a file should be deleted with the d key, I see that it's marking the files as to be deleted, I have a server running and this is the beginnig of the log for it:

2016/11/13 21:30:51 hi!
2016/11/13 21:30:51 listen: conn 1000
2016/11/13 21:30:52 listen: save move /home/user/scrot.png
2016/11/13 21:30:52 listen: send sync

But the file continues to be there. What's the procedure for deleting a file? I have a custom mapping right now but it's suboptimal.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.