2

I would like to use opening books for my stockfish chess engine, but I'm not sure how to do this. As far as I understand stockfish doesn't support these, so I though I setup a system next to stockfish, which is used until it doesn't return any moves anymore.

These .bin files can be found anywhere, for example

http://rebel13.nl/download/books.html

or

https://github.com/joeyrobert/ceruleanjs_opening_books

Anyway, I downloaded a couple of .bin files, and thought to use it with polyglot-chess

var Polyglot = require('polyglot-chess');

var obj = new Polyglot();

var fen = "rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1";
console.log("Polyglot hash for fen " + fen + " is: " + obj.hash(fen));
console.log("Best move in the book is: " + obj.find(fen, "book.bin", true));
console.log("Random move in the book is: " + obj.find(fen, "book.bin", false));

Now when I try to run it

$> node index.js 
internal/modules/cjs/loader.js:615
   throw err;
   ^

Error: Cannot find module '../build/Release/polyglot'
    at Function.Module._resolveFilename (internal/modules/cjs/loader.js:613:15)
...

I checked the build folder from polyglot-chess, but there isn't a polyglot file at that location.

  • 1
    I'm not sure what you mean by "needs a polyglot tool". From what I can see, the polyglot-chess package is capable of reading the binary files without any external tool. – ProgramFOX Jun 18 at 5:56
  • My mistake. It seems that polyglot-chess ships with all the files needed. But I get the impression it still needs to be build – Jeanluca Scaljeri Jun 18 at 6:53
  • I also update my post with more details of the issue I have – Jeanluca Scaljeri Jun 18 at 7:00
  • Right, I see. It has to compile the native C++ file first, and that's what it's failing at for me when doing npm install. Not too surprising actually, considering the age of the package... – ProgramFOX Jun 18 at 7:16
3

You can do this on your own in a customized fashion (i.e. you control when to run the engine or to use the book) with a bit of scripting in python, using the python-chess module and a polyglot opening book of your choice. In this example I'm using gm2001.bin, which you can get from here.

As dummy example I have chosen two positions:

  • fen = 'rnbqkb1r/ppp1pppp/5n2/3p4/3P4/5NP1/PPP1PP1P/RNBQKB1R b KQkq - 0 3' A basic Catalan position for which I know the book still has a move.
  • fen2 = 'rnbqkb1r/ppp1ppp1/5n2/3p3p/3P4/5NP1/PPP1PP1P/RNBQKB1R w KQkq - 0 4' A position for which there are no book moves left in the chosen opening book.

What the code does is very basic: if it finds an opening move, then it makes that move (if there are more opening branches, you need to figure out how you want to choose the line to play), otherwise, it calls Stockfish with 10 seconds of movetime and makes the top engine move.

import chess
import chess.uci
import chess.polyglot

fen = 'rnbqkb1r/ppp1pppp/5n2/3p4/3P4/5NP1/PPP1PP1P/RNBQKB1R b KQkq - 0 3'
fen2 = 'rnbqkb1r/ppp1ppp1/5n2/3p3p/3P4/5NP1/PPP1PP1P/RNBQKB1R w KQkq - 0 4'
board = chess.Board(fen)
print board

handler = chess.uci.InfoHandler()
engine = chess.uci.popen_engine('stockfish_8_x64') #Provide correct address to where your engine is stored
evaltime = 10000

reader = chess.polyglot.open_reader('gm2001.bin') #Provide correct address to where your bin file is stored
n = sum(1 for _ in reader.find_all(board))

if n==0:
    print 'empty, using SF top move with 10 sec movetime'
    engine.info_handlers.append(handler)
    if board.is_checkmate():
        print 'Game has ended: checkmate'
    else:
        engine.position(board)
        eval = engine.go(movetime=evaltime)
        nextmove = board.san(eval[0])
        if handler.info["score"][1].cp != None:
            print 'Top move: ', nextmove, ' Evaluation: ',round(handler.info["score"][1].cp/100.0,2)
        else:
            print nextmove
        print board.variation_san(handler.info["pv"][1])
        print 'nodes: ', handler.info["nodes"], ' depth: ', handler.info["depth"], ' time: ', handler.info["time"]
        board.push_san(nextmove)
        print '---- Updated position:'
        print board
else:
    for entry in reader.find_all(board):
        print 'Found book moves:'
        nextmove = board.san(entry.move())
        print str(nextmove)
        board.push_san(nextmove)
        print '---- Updated position:'
        print board
        break

Output for the first fen:

r n b q k b . r
p p p . p p p p
. . . . . n . .
. . . p . . . .
. . . P . . . .
. . . . . N P .
P P P . P P . P
R N B Q K B . R
Found book moves:
c6
---- Updated position:
r n b q k b . r
p p . . p p p p
. . p . . n . .
. . . p . . . .
. . . P . . . .
. . . . . N P .
P P P . P P . P
R N B Q K B . R

and output for the 2nd fen (fen2):

r n b q k b . r
p p p . p p p .
. . . . . n . .
. . . p . . . p
. . . P . . . .
. . . . . N P .
P P P . P P . P
R N B Q K B . R
empty, using SF top move with 10 sec movetime
Top move:  Bg2  Evaluation:  0.24
4. Bg2 c5 5. c4 cxd4 6. cxd5 Qxd5 7. Qxd4 Nc6 8. Qxd5 Nxd5 9. Bd2 Ndb4 10. Na3 Be6 11. Ng5 Bd5 12. Bxd5 Nxd5 13. e4 Ndb4 14. Nb5 Nd3+ 15. Ke2
nodes:  14946976  depth:  21  time:  10001
---- Updated position:
r n b q k b . r
p p p . p p p .
. . . . . n . .
. . . p . . . p
. . . P . . . .
. . . . . N P .
P P P . P P B P
R N B Q K . . R

You should be able to take it from here and extend the code however you want.

  • Thanks a lot! Unfortunate, I'm a python noob, and have an issue running this code. I'm using python3/pip3 and installed the chess module: pip install python-chess Furthermore I had to change all the print statements from print .... to print(....). I don't know why! But now I have an error which I don't know how to solve, it cannot find chess.uci: No module named 'chess.uci' Any suggestions why that is? – Jeanluca Scaljeri Jun 18 at 21:00
  • 2
    No problem. I am using Python 2.7 still, and you have python 3 it seems, that's why you had to change the print commands. The chess.uci error seems to simply mean you haven't installed the additional packages, try something like pip install python-chess[uci] (or in your case pip3). In the newer versions of python-chess uci has been replaced by engine, so try also pip3 install python-chess[engine] and then see the related docs for possible syntax changes using the newest version. Let me know if you're still stuck. – Phonon Jun 18 at 21:31
  • Check, I have it working now. Thanks a lot!! – Jeanluca Scaljeri Jun 19 at 8:03

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.