Download Full (Ebook) Jasmine JavaScript Testing, 2nd Edition_ Test your JavaScript applications efficiently using Jasmine and React.js by kan PDF All Chapters
Download Full (Ebook) Jasmine JavaScript Testing, 2nd Edition_ Test your JavaScript applications efficiently using Jasmine and React.js by kan PDF All Chapters
com
https://ebooknice.com/product/jasmine-javascript-
testing-2nd-edition-test-your-javascript-applications-
efficiently-using-jasmine-and-react-js-50195432
OR CLICK HERE
DOWLOAD EBOOK
https://ebooknice.com/product/javascript-cookbook-2nd-edition-
programming-the-web-50195402
ebooknice.com
https://ebooknice.com/product/learning-javascript-3e-50195302
ebooknice.com
(Ebook) Reactive Programming with JavaScript by kan
https://ebooknice.com/product/reactive-programming-with-
javascript-50194990
ebooknice.com
https://ebooknice.com/product/react-js-book-learning-react-javascript-
library-from-scratch-7159540
ebooknice.com
ebooknice.com
www.it-ebooks.info
Jasmine JavaScript Testing
Second Edition
Paulo Ragonha
BIRMINGHAM - MUMBAI
www.it-ebooks.info
Jasmine JavaScript Testing
Second Edition
All rights reserved. No part of this book may be reproduced, stored in a retrieval
system, or transmitted in any form or by any means, without the prior written
permission of the publisher, except in the case of brief quotations embedded in
critical articles or reviews.
Every effort has been made in the preparation of this book to ensure the accuracy
of the information presented. However, the information contained in this book is
sold without warranty, either express or implied. Neither the author, nor Packt
Publishing, and its dealers and distributors will be held liable for any damages
caused or alleged to be caused directly or indirectly by this book.
Packt Publishing has endeavored to provide trademark information about all of the
companies and products mentioned in this book by the appropriate use of capitals.
However, Packt Publishing cannot guarantee the accuracy of this information.
ISBN 978-1-78528-204-1
www.packtpub.com
www.it-ebooks.info
Credits
Reviewers Proofreaders
Hany A. Elemary Paul Hindle
Ryzhikov Maksim Linda Morris
Veer Shubhranshu Shrivastav
Sergey Simonchik Indexer
Tejal Soni
Commissioning Editor
Amarabha Banerjee Production Coordinator
Aparna Bhagat
Acquisition Editor
Larissa Pinto Cover Work
Aparna Bhagat
Technical Editor
Anushree Arun Tendulkar
Copy Editor
Sarang Chari
www.it-ebooks.info
About the Author
He loves to hack, so you will often see him wandering around in conferences or
attending hackathons. His most recent professional experiences ranged from DevOps
(with Chef and Docker) to moving up the stack with Node.js, Ruby, and Python and
all the way toward building single-page applications (mostly with Backbone.js and
"ad hoc" solutions).
Passionate about automation, he sees testing as a liberating tool to enjoy the craft of
writing code even more. Back in 2013, he wrote the first edition of the book Jasmine
JavaScript Testing, Packt Publishing.
Paulo has an amazing wife, who he loves very much. He lives in beautiful
Florianópolis, a coastal city in the south of Brazil. He is a casual speaker, a biker,
a runner, and a hobbyist photographer.
www.it-ebooks.info
About the Reviewers
His brother invited him to join the team that developed programs for American
hospitals, as an HTML developer.
Ryzhikov started with developing a simple, static site for hospitals and then studied
JavaScript, Ruby, and SQL and worked as a full-stack developer. In 5 years of work
in the area of IT, he has worked in various projects and teams. He developed medical
systems, dating sites, web mail (Yandex.Mail), and now he helps develop tools for
developers at JetBrains.
www.it-ebooks.info
Veer Shubhranshu Shrivastav is an Indian software developer working
with Tata Consultancy Services since 2013 and is a former research intern at IIIT-
Delhi. He has worked on different technologies, such as PHP, Moodle, jQuery,
AngularJS, RequireJS, Android, Jasmine, Ionic, and so on, and also takes an interest
in cryptography, network security, and database technologies. He has worked with
various Indian IT start-ups, helping them as a software architect.
With his interest in the open source community, he developed a Pro*C library
named CODBC, which is available at http://codbc.com. The library enables
an object-oriented approach to connect C++ and Oracle Database.
www.it-ebooks.info
www.PacktPub.com
Support files, eBooks, discount offers,
and more
For support files and downloads related to your book, please visit www.PacktPub.com.
Did you know that Packt offers eBook versions of every book published, with PDF and
ePub files available? You can upgrade to the eBook version at www.PacktPub.com and
as a print book customer, you are entitled to a discount on the eBook copy. Get in touch
with us at [email protected] for more details.
At www.PacktPub.com, you can also read a collection of free technical articles, sign up
for a range of free newsletters and receive exclusive discounts and offers on Packt books
and eBooks.
TM
https://www2.packtpub.com/books/subscription/packtlib
Do you need instant solutions to your IT questions? PacktLib is Packt's online digital
book library. Here, you can search, access, and read Packt's entire library of books.
Why subscribe?
• Fully searchable across every book published by Packt
• Copy and paste, print, and bookmark content
• On demand and accessible via a web browser
www.it-ebooks.info
www.it-ebooks.info
Table of Contents
Preface v
Chapter 1: Getting Started with Jasmine 1
JavaScript – the bad parts 1
Jasmine and behavior-driven development 3
Downloading Jasmine 4
Summary 6
Chapter 2: Your First Spec 7
The Investment Tracker application 7
Jasmine basics and thinking in BDD 8
Setup and teardown 14
Nested describes 18
Setup and teardown 19
Coding a spec with shared behavior 19
Understanding matchers 20
Custom matchers 21
Built-in matchers 26
Summary 32
Chapter 3: Testing Frontend Code 33
Thinking in terms of components (Views) 34
The module pattern 35
Using HTML fixtures 36
Basic View coding rules 40
The View should encapsulate a DOM element 41
Integrating Views with observers 43
Testing Views with jQuery matchers 48
The toBeMatchedBy jQuery matcher 49
The toContainHtml jQuery matcher 50
The toContainElement jQuery matcher 50
[i]
www.it-ebooks.info
Table of Contents
www.it-ebooks.info
Table of Contents
[ iii ]
www.it-ebooks.info
www.it-ebooks.info
Preface
This book is about being a better JavaScript developer. So, throughout the chapters,
you will not only learn about writing tests in the Jasmine 'idiom', but also about
the best practices in writing software in the JavaScript language. It is about
acknowledging JavaScript as a real platform for application development and
leveraging all its potential. It is also about tooling and automation and how to make
your life easier and more productive.
Most importantly, this book is about craftsmanship of not only working software,
but also well-crafted software.
Over the course of the chapters, the concept of test-driven development is explained
through the development of a simple stock market Investment Tracker application. It
starts with the basics of testing through the development of the base domain classes
(such as stock and investment), passes through the concepts of maintainable browser
code, and concludes with a full refactoring to a React.js application build on ECMA
Script 6 modules and automated build.
[v]
www.it-ebooks.info
Preface
Chapter 2, Your First Spec, helps you learn the thought process behind thinking
in terms of test-driven development. You will code your very first JavaScript
functionality driven by tests. You will also learn the basic functions of Jasmine
and how to structure your tests. Also demonstrated, is how Jasmine matchers work
and how you can create one of your own to improve your tests' code readability.
Chapter 4, Asynchronous Testing – AJAX, talks about the challenges in testing AJAX
requests and how you can use Jasmine to test any asynchronous code. You will learn
about Node.js and how to create a very simple HTTP server to use as a fixture to
your tests.
Chapter 5, Jasmine Spies, presents the concept of test doubles and how to use spies to
do behavior checking.
Chapter 6, Light Speed Unit Testing, helps you to learn about the issues with AJAX
testing and how you can make your tests run faster using stubs or fakes.
Chapter 7, Testing React Applications, introduces you to React, a library to build user
interfaces, and covers how you can use it to improve the concepts presented in
Chapter 3, Testing Frontend Code, to create richer and more maintainable applications,
of course, driven by tests.
Chapter 8, Build Automation, presents you with the power of automation. It introduces
you to webpack, a bundling tool for frontend assets. You will start to think in terms
of modules and their dependencies, and you will learn how to code your tests as
modules. You will also learn about packing and minifying the code to production
and how to automate this process. Finally, you are going to learn about running your
tests from a command line and how this can be used in a continuous integration
environment with Travis.ci.
[ vi ]
www.it-ebooks.info
Preface
Conventions
In this book, you will find a number of text styles that distinguish between different
kinds of information. Here are some examples of these styles and an explanation of
their meaning.
Code words in text, database table names, folder names, filenames, file extensions,
pathnames, dummy URLs, user input, and Twitter handles are shown as follows:
"We can include other contexts through the use of the include directive."
When we wish to draw your attention to a particular part of a code block, the relevant
lines or items are set in bold:
describe("Investment", function() {
it("should be of a stock", function() {
expect(investment.stock).toBe(stock);
});
});
New terms and important words are shown in bold. Words that you see on
the screen, for example, in menus or dialog boxes, appear in the text like this:
"Clicking the Next button moves you to the next screen."
[ vii ]
www.it-ebooks.info
Preface
Reader feedback
Feedback from our readers is always welcome. Let us know what you think about
this book—what you liked or disliked. Reader feedback is important for us as it helps
us develop titles that you will really get the most out of.
If there is a topic that you have expertise in and you are interested in either writing
or contributing to a book, see our author guide at www.packtpub.com/authors.
Customer support
Now that you are the proud owner of a Packt book, we have a number of things to
help you to get the most from your purchase.
[ viii ]
www.it-ebooks.info
Preface
Errata
Although we have taken every care to ensure the accuracy of our content, mistakes
do happen. If you find a mistake in one of our books—maybe a mistake in the text or
the code—we would be grateful if you could report this to us. By doing so, you can
save other readers from frustration and help us improve subsequent versions of this
book. If you find any errata, please report them by visiting http://www.packtpub.
com/submit-errata, selecting your book, clicking on the Errata Submission Form
link, and entering the details of your errata. Once your errata are verified, your
submission will be accepted and the errata will be uploaded to our website or added
to any list of existing errata under the Errata section of that title.
Piracy
Piracy of copyrighted material on the Internet is an ongoing problem across all
media. At Packt, we take the protection of our copyright and licenses very seriously.
If you come across any illegal copies of our works in any form on the Internet, please
provide us with the location address or website name immediately so that we can
pursue a remedy.
We appreciate your help in protecting our authors and our ability to bring you
valuable content.
Questions
If you have a problem with any aspect of this book, you can contact us at
[email protected], and we will do our best to address the problem.
[ ix ]
www.it-ebooks.info
www.it-ebooks.info
Getting Started with Jasmine
It is an exciting time to be a JavaScript developer; technologies have matured,
web browsers are more standardized, and there are new things to play with every
day. JavaScript has become an established language, and the Web is the true
open platform of today. We've seen the rise of single-page web applications, the
proliferation of Model View Controller (MVC) frameworks, such as Backbone.js
and AngularJS, the use of JavaScript on the server with Node.js, and even mobile
applications created entirely with HTML, JavaScript, and CSS using technologies
such as PhoneGap.
From its humble beginnings with handling HTML forms, to the massive applications
of today, the JavaScript language has come very far, and with it, a number of tools
have matured to ensure that you can have the same level of quality with it that you
have with any other language.
This book is about the tools that keep you in control of your JavaScript development.
[1]
www.it-ebooks.info
Getting Started with Jasmine
Besides that, you have issues with the language itself. Brendan Eich developed
JavaScript in just 10 days, under a lot of management pressure at Netscape. Although
it got itself right in its simplicity, first-class functions, and object prototypes, it also
introduced some problems with the attempt to make the language malleable and
allow it to evolve.
Every JavaScript object is mutable; this means that there is nothing you can do to
prevent a module from overwriting pieces of other modules. The following code
illustrates how simple it is to overwrite the global console.log function:
console.log('test');
>> 'test'
console.log = 'break';
console.log('test');
>> TypeError: Property 'log' of object #<Console> is not a function
This was a conscious decision on the language design; it allows developers to tinker
and add missing functionality to the language. But given such power, it is relatively
easy to make a mistake.
Another problem, is with how JavaScript deals with type. In other languages, an
expression like '1' + 1 would probably raise an error; in JavaScript, due to some
non-intuitive type coercion rules, the aforementioned code results in '11'. But the
main problem is in its inconsistency; on multiplication, a string is converted into a
number, so '3' * 4, is actually 12.
This can lead to some hard-to-find problems on big expressions. Suppose you have
some data coming from a server, and although you are expecting numbers, one value
came as a string:
var a = 1, b = '2', c = 3, d = 4;
var result = a + b + c * d;
These are just two common problems faced by developers. Throughout the book,
you are going to apply best practices and write tests to guarantee that you don't fall
into these, and other, pitfalls.
[2]
www.it-ebooks.info
Chapter 1
But before we can go any further, first we need to get some fundamentals right,
starting with what a test unit is.
A test unit is a piece of code that tests a functionality unit of the application code. But
sometimes, it can be tricky to understand what a functionality unit can be, so for that
reason, Dan North came up with a solution in the form of BDD, which is a rethink of
test-driven development (TDD).
In traditional unit testing practice, the developer is left with loose guidelines on how
to start the process of testing, what to test, how big a test should be, or even how to
call a test.
To fix these problems, Dan took the concept of user stories from the standard agile
construct, as a model on how to write tests.
For example, a music player application could have an acceptance criterion such as:
Given a player, when the song has been paused, then it should indicate that the
song is currently paused.
In Jasmine, this translates into a very expressive language that allows tests to be
written in a way that reflects actual business values. The preceding acceptance
criterion written as a Jasmine test unit would be as follows:
describe("Player", function() {
describe("when song has been paused", function() {
it("should indicate that the song is paused", function() {
});
});
});
[3]
www.it-ebooks.info
Getting Started with Jasmine
You can see how the criterion translates well into the Jasmine syntax. In the next
chapter, we will get into the details of how these functions work.
With Jasmine, as with other BDD frameworks, each acceptance criterion directly
translates to a test unit. For that reason, each test unit is usually called a spec, short
for specification. During the course of this book, we will be using this terminology.
Downloading Jasmine
Getting started with Jasmine is actually pretty simple.
While at the Jasmine website, you might notice that it is actually a live page
executing the specs contained in it. This is made possible by the simplicity of the
Jasmine framework, allowing it to be executed in the most diverse environments.
After you've downloaded the distribution and uncompressed it, you can open the
SpecRunner.html file on your browser. It will show the results of a sample test
suite (including the acceptance criterion we showed you earlier):
This SpecRunner.html file is a Jasmine browser spec runner. It is a simple HTML file
that references the Jasmine code, the source files, and the test files. For convention
purposes, we are going to refer to this file simply as runner.
[4]
www.it-ebooks.info
Chapter 1
You can see how simple it is by opening it on a text editor. It is a small HTML file
that references the Jasmine source:
<script src="lib/jasmine-2.1.3/jasmine.js"></script>
<script src="lib/jasmine-2.1.3/jasmine-html.js"></script>
<script src="lib/jasmine-2.1.3/boot.js"></script>
The runner references a special SpecHelper.js file that contains code shared
between specs:
<script type="text/javascript" src="spec/SpecHelper.js"></script>
Although, for now, we are running the specs in the browser, in Chapter 8, Build
Automation, we are going to make the same specs and code run on a headless
browser, such as PhantomJS, and have the results written on the console.
And although not covered in this book, Jasmine can also be used to test server-side
JavaScript code written for environments such as Node.js.
This Jasmine flexibility is amazing, because you can use the same tool to test all sorts
of JavaScript code.
[5]
www.it-ebooks.info
Getting Started with Jasmine
Summary
In this chapter, you saw some of the motivations behind testing a JavaScript
application. I showed you some common pitfalls of the JavaScript language
and how BDD and Jasmine both help you to write better tests.
You have also seen how easy it is to download and get started with Jasmine.
In the next chapter, you are going to learn how to think in BDD and code your
very first spec.
[6]
www.it-ebooks.info
Your First Spec
This chapter is about the basics, and we are going to guide you through how to write
your first spec, think in test-first terms for development, and also show you all the
available global Jasmine functions. By the end of the chapter, you should know how
Jasmine works and be ready to start doing your first tests by yourself.
The following screenshot of the form illustrates how a user might create a new
investment on this application:
This form will allow the input of three values that define an investment:
• First, we will input Symbol, which represents which company (stock) the
user is investing in
• Then, we will input how many Shares the user has bought (or invested in)
• Finally, we will input how much the user has paid for each share
(Share price)
[7]
www.it-ebooks.info
Your First Spec
If you are unfamiliar with how the stock market works, imagine you are shopping
for groceries. To make a purchase, you must specify what you are buying, how many
items you are buying, and how much you are going to pay. These concepts translate
to an investment as:
Once the user has added an investment, it must be listed along with their other
investments, as shown in the following screenshot:
The idea is to display how well their investments are going. Since the prices of the
stocks fluctuate over time, the difference between the price the user has paid and
the current price indicates whether it is a good (profit) or a bad (loss) investment.
In the preceding screenshot, we can see that the user has two investments:
This is a very simple application, and we will get a deeper understanding of its
functionality as we go on with its development.
[8]
www.it-ebooks.info
Chapter 2
Using the standalone distribution downloaded in the previous chapter, the first
thing we need to do is create a new spec file. This file can be created anywhere,
but it is a good idea to stick to a convention, and Jasmine already has a good one:
specs should be in the /spec folder. Create an InvestmentSpec.js file and add
the following lines:
describe("Investment", function() {
});
The describe function is a global Jasmine function used to define test contexts.
When used as the first call in a spec, it creates a new test suite (a collection of test
cases). It accepts two parameters, which are as follows:
});
});
[9]
www.it-ebooks.info
Your First Spec
Execute the spec by opening the runner on the browser. The following output
can be seen:
It might sound strange to have an empty spec passing, but in Jasmine, as with other
test frameworks, a failed assertion is required to make the spec fail.
An assertion (or expectation) is a comparison between two values that must result
in a boolean value. The assertion is only considered a success if the result of the
comparison is true.
In Jasmine, assertions are written using the global Jasmine function expect, along
with a matcher that indicates what comparison must be made with the values.
Regarding the current spec (it is expected that the investment is of a stock), in
Jasmine this translates to the following code:
describe("Investment", function() {
it("should be of a stock", function() {
expect(investment.stock).toBe(stock);
});
});
Add the preceding highlighted code to the InvestmentSpec.js file. The expect
function takes only one parameter, which defines the actual value, or in other words,
what is going to be tested—investment.stock—and expects the chaining call to a
matcher function, which in this case is toBe. That defines the expected value, stock,
and the comparison method to be performed (to be the same).
Behind the scenes, Jasmine makes a comparison to check whether the actual value
(investment.stock) and expected value (stock) are the same, and if they are not,
the test fails.
[ 10 ]
www.it-ebooks.info
Chapter 2
With the assertion written, the spec that previously passed has now failed, as shown
in the following screenshot:
This spec failed because, as the error message states, investment is not defined.
The idea here is to do only what the error is indicating us to do, so although you
might feel the urge to write something else, for now let's just create this investment
variable with an Investment instance in the InvestmentSpec.js file, as follows:
describe("Investment", function() {
it("should be of a stock", function() {
var investment = new Investment();
expect(investment.stock).toBe(stock);
});
});
Don't worry that the Investment() function doesn't exist yet; the spec is about to
ask for it on the next run, as follows:
You can see that the error has changed to Investment is not defined. It now asks
for the Investment function. So, create a new Investment.js file in the src folder
and add it to the runner, as shown in the following code:
<!-- include source files here... -->
<script type="text/javascript" src="src/Investment.js"></script>
[ 11 ]
www.it-ebooks.info
Your First Spec
This makes the error change. It now complains about the missing stock variable, as
shown in the following screenshot:
One more time, we feed the code it is asking for into the InvestmentSpec.js file,
as shown in the following code:
describe("Investment", function() {
it("should be of a stock", function() {
var stock = new Stock();
var investment = new Investment();
expect(investment.stock).toBe(stock);
});
});
The error changes again; this time it is about the missing Stock function:
Create a new file in the src folder, name it Stock.js, and add it to the runner. Since
the Stock function is going to be a dependency of Investment, we should add it just
before Investment.js:
<!-- include source files here... -->
<script type="text/javascript" src="src/Stock.js"></script>
<script type="text/javascript" src="src/Investment.js"></script>
[ 12 ]
www.it-ebooks.info
Chapter 2
Finally, the error is about the expectation, as shown in the following screenshot:
To fix this and complete this exercise, open the Investment.js file inside the src
folder, and add the reference to the stock parameter:
function Investment (stock) {
this.stock = stock;
};
The drive to write code must come from a spec that has failed. You
must not write code unless its purpose is to fix a failed spec.
[ 13 ]
www.it-ebooks.info
Your First Spec
describe("Investment", function() {
it("should be of a stock", function() {
var stock = new Stock();
var investment = new Investment({
stock: stock,
shares: 100
});
expect(investment.stock).toBe(stock);
});
You can see that apart from having written the new spec, we have also changed the
call to the Investment constructor to support the new shares parameter.
[ 14 ]
www.it-ebooks.info
Chapter 2
The code is now refactored. We can run the tests to see that only the new spec fails,
as shown here:
To fix this, change the Investment constructor to make the assignment to the shares
property, as follows:
function Investment (params) {
this.stock = params.stock;
this.shares = params.shares;
};
But as you can see, the following code, which instantiates Stock and Investment, is
duplicated on both specs:
var stock = new Stock();
var investment = new Investment({
stock: stock,
shares: 100
});
[ 15 ]
www.it-ebooks.info
Your First Spec
Refactor the previous specs by extracting the setup code using the beforeEach
function:
describe("Investment", function() {
var stock, investment;
beforeEach(function() {
stock = new Stock();
investment = new Investment({
stock: stock,
shares: 100
});
});
This looks much cleaner; we not only removed the code duplication, but also
simplified the specs. They became much easier to read and maintain since their
only responsibility now is to fulfill the expectation.
There is also a teardown function (afterEach) that sets the code to be executed after
each spec. It is very useful in situations where a cleanup is required after each spec.
We will see an example of its application in Chapter 6, Light Speed Unit Testing.
To finish the specification of Investment, add the remaining two specs to the
InvestmentSpec.js file, inside the spec folder:
describe("Investment", function() {
var stock;
var investment;
beforeEach(function() {
stock = new Stock();
investment = new Investment({
stock: stock,
shares: 100,
sharePrice: 20
[ 16 ]
www.it-ebooks.info
Chapter 2
});
});
Run the specs to see them fail, as shown in the following screenshot:
Add the following code to fix them in the Investment.js file inside the src folder:
function Investment (params) {
this.stock = params.stock;
this.shares = params.shares;
this.sharePrice = params.sharePrice;
this.cost = this.shares * this.sharePrice;
};
[ 17 ]
www.it-ebooks.info
Your First Spec
Run the specs for the last time to see them pass:
It is important to always see a spec fail before writing the code to fix it;
otherwise, how would you know that you really need to fix it? Imagine
this as a way to test the test.
Nested describes
Nested describes are useful when you want to describe similar behavior between
specs. Suppose we want the following two new acceptance criteria:
• Given an investment, when its stock share price valorizes, it should have
a positive return on investment (ROI)
• Given an investment, when its stock share price valorizes, it should be
a good investment
Both these criteria share the same behavior when the investment's stock share
price valorizes.
To translate this into Jasmine, you can nest a call to the describe function inside the
existing one in the InvestmentSpec.js file (I removed the rest of the code for the
purpose of demonstration; it is still there):
describe("Investment", function()
describe("when its stock share price valorizes", function() {
});
});
It should behave just like the outer one, so you can add specs (it) and use the setup
and teardown functions (beforeEach, afterEach).
[ 18 ]
www.it-ebooks.info
Chapter 2
So, we can add a setup function to this new describe function that changes the
share price of the stock, so that it's greater than the share price of the investment:
describe("Investment", function() {
var stock;
var investment;
beforeEach(function() {
stock = new Stock();
investment = new Investment({
stock: stock,
shares: 100,
sharePrice: 20
});
});
[ 19 ]
www.it-ebooks.info
Your First Spec
Investment.prototype.isGood = function() {
return this.roi() > 0;
};
You can run the specs and see that they pass:
Understanding matchers
By now, you've already seen plenty of usage examples for matchers and probably
can feel how they work.
You have seen how to use the toBe and toEqual matchers. These are the two
base built-in matchers available in Jasmine, but we can extend Jasmine by writing
matchers of our own.
So, to really understand how Jasmine matchers work, we need to create one ourselves.
[ 20 ]
www.it-ebooks.info
Chapter 2
Custom matchers
Consider this expectation from the previous section:
expect(investment.isGood()).toEqual(true);
Although it works, it is not very expressive. Imagine if we could instead rewrite it as:
expect(investment).toBeAGoodInvestment();
Although you can put this new matcher definition inside the InvestmentSpec.js
file, Jasmine already has a default place to add custom matchers, the SpecHelper.js
file, inside the spec folder. If you are using Standalone Distribution, it already comes
with a sample custom matcher; delete it and let's start from scratch.
The function being defined here is not the matcher itself but a factory function
to build the matcher. Its purpose, once called is to return an object containing a
compare function, as follows:
jasmine.addMatchers({
toBeAGoodInvestment: function () {
return {
compare: function (actual, expected) {
// matcher definition
}
};
}
});
[ 21 ]
www.it-ebooks.info
Your First Spec
The compare function will contain the actual matcher implementation, and as can be
observed by its signature, it receives both values being compared (the actual and
expected values).
For the given example, the investment object will be available in the
actual argument.
Then, Jasmine expects, as the result of this compare function, an object with a pass
attribute with a boolean value true to indicate that the expectation passes and
false if the expectation fails.
After the change, the specs should still pass. But what happens if a spec fails? What
is the error message that Jasmine reports?
[ 22 ]
www.it-ebooks.info
Chapter 2
When running the specs again, Jasmine generates an error message stating Expected
{ stock: { sharePrice: 40 }, shares: 100, sharePrice: 20, cost: 2000
} to be a good investment, as shown in the following screenshot:
Jasmine does a great job generating this error message, but it also allows its
customization via the result.message property of the object returned as the
result of the matcher. Jasmine expects this property to be a string with the
following error message:
toBeAGoodInvestment: function () {
return {
compare: function (actual, expected) {
var result = {};
result.pass = actual.isGood();
result.message = 'Expected investment to be a good investment';
return result;
}
};
}
Run the specs again and the error message should change:
[ 23 ]
www.it-ebooks.info
Your First Spec
Implement this new acceptance criterion in the InvestmentSpec.js file inside the
spec folder by adding new and nested describe and spec, as follows:
But there is a catch! Let's break the investment implementation in the Investment.
js file code so that it is always a good investment, as follows:
Investment.prototype.isGood = function() {
return true;
};
After running the specs again, you can see that this new spec fails, but the error
message, Expected investment to be a good investment, is wrong, as
shown in the following screenshot:
That is the message that was hardcoded inside the matcher. To fix this, you need to
make the message dynamic.
Jasmine only shows the message if the matcher fails, so the proper way of making
this message dynamic is to consider what message is supposed to be shown when
the given comparison is invalid:
compare: function (actual, expected) {
var result = {};
result.pass = actual.isGood();
[ 24 ]
www.it-ebooks.info
Chapter 2
if (actual.isGood()) {
result.message = 'Expected investment to be a bad investment';
} else {
result.message = 'Expected investment to be a good investment';
}
return result;
}
Before continuing in the chapter, change the isGood method back again to its correct
implementation:
Investment.prototype.isGood = function() {
return this.roi() > 0;
};
What this example lacked was a way to show how to pass an expected value to a
matcher like this:
expect(investment.cost).toBe(2000)
It turns out that a matcher can receive any number of expected values as parameters.
So, for instance, the preceding matcher could be implemented in the SpecHelper.js
file, inside the spec folder, as follows:
beforeEach(function() {
jasmine.addMatchers({
toBe: function () {
return {
compare: function (actual, expected) {
return actual === expected;
}
};
}
});
});
[ 25 ]
www.it-ebooks.info
Your First Spec
By implementing any matcher, check first whether there is one available that already
does what you want.
For more information, check the official documentation at the Jasmine website
http://jasmine.github.io/2.1/custom_matcher.html.
Built-in matchers
Jasmine comes with a bunch of default matchers covering the basis of value checking
in the JavaScript language. To understand how they work and where to use them
properly is a journey of how JavaScript handles type.
It works for all primitive values (number, string, and boolean) as well as any object
(including arrays), as shown in the following code:
describe("toEqual", function() {
it("should pass equal numbers", function() {
expect(1).toEqual(1);
});
[ 26 ]
www.it-ebooks.info
Random documents with unrelated
content Scribd suggests to you:
CHAPTER XVI.
I AM 'DON ALONZO.'
It was a splendid evening one day towards the end of the year 1503,
when a tall, plainly-attired, handsome youth drew near the home of a
Spanish colonist to whom he had notes of introduction. He had
walked out to it from San Domingo, a distance of some five miles,
and now stood still to survey the scene, his hand resting on a dog's
head the while that had accompanied him.
"It is a glorious place, old Don," he muttered in a tone of
considerable satisfaction, although it betokened great surprise as
well.
And a glorious place it was, and most especially beautiful now that
the long, low houses of stone and earth, the waving palms, and all
the other luxuriance of that southern clime, were bathed in the
golden glory of a southern sunset. In a cushioned reclining chair,
placed in a shady spot of the broad verandah, lounged a young man,
handsome, but for a Spaniard coarse-featured and rather thick-set.
However, all defects of person were thrown into the background by a
sumptuousness of attire that fairly startled the youth as he at length
approached, and delivered his letters.
"And you are the son of Master Pedro, the spice-dealer of El Cuevo!"
he breathed forth at last.
The words of that ejaculation were common-place enough, but the
tone in which they were uttered, and the look with which they were
accompanied, made them so inexpressibly gratifying, and at the
same time comical, to the man to whom they were addressed, that
he burst into a loud, long laugh before vouchsafing them any other
answer.
"Yes, yes," he said at last, recovering himself with an easy
nonchalance. "Yes, yes, youngster, I do not mind confessing to you,
since you know the fact before my confession, that the worthy old
gentleman yonder, with his frugal fare, and his better stuff cloak for
holidays, is my father, and a rare good old miser he is, to save the
maravedis for my spending. But mind ye, that is between you and
me and Saint Peter."
A wondering gaze from a great pair of thoughtful, brilliant eyes was
the questioning reply to this intimation. "And for the rest of the
world," asked the owner of the eyes after a short pause, "who is your
father for the rest of the world?"
Another laugh greeted this query.
"Why, for the rest of the world, being what you have found me, Don
Alonzo de Loyala, my father is, like thine own, some long-deceased
grandee of Spain, who neglected his duty towards his son as
regarded the due endowment of riches to maintain my rank in mine
own land."
As this mocking speech ended, Montoro de Diego's cheeks flushed
angrily, and he exclaimed—
"Do you then imply that my claims to noble birth are thus also
assumed? By St.—"
"Nay then, nay," good-humouredly interrupted the other. "In these
latitudes it is not well for health to heat thyself for nought. Keep thy
passion for the red rascals, who are so lazy that they'll die rather
than live and work. I imply nothing to thy detriment. Wert thou placed
as I am, then wouldst thou also have a wealthy father at thy back, to
help thee to maintain that rank out here it should pleasure thee to
claim. Meantime, I do no more than half of those around me, and
with better right; for I am no released felon, and I deal honestly by
those I trade with. I will deal honestly with you. Twice have I had
advices from my father, and from good master Sancho, that I should
try to secure you for a companion and aid, should you elect to
remain here on the Admiral's return to Spain. And I like you at first
sight well enough to be willing to take their advice. Will you stay with
me then, or shall I help you to find friends elsewhere?"
Montoro looked at the man from head to foot slowly and earnestly,
as he lounged there before him, so great a contrast to himself, and
then as slowly and earnestly said—
"I agree to stay—for a time."
"Umph!" muttered the self-styled Don Alonzo, somewhat taken
aback in his turn. "Umph! my noble youngster, methinks from your air
you suppose the obligation to be rather more mutual than I esteem it.
You are a beggar and friendless, and I—am not."
However, Montoro was not now so friendless as his new colleague
assumed. Had he returned to Spain, even there he might now have
been found some sort of employment, and out in the Colony the
spirited young adventurer, with a pair of hands both able and willing
to work, could have easily found some more indolent seeker after
wealth willing to go into partnership with him. But Rachel de Diego
was sheltered under the roof of the spice-merchant, and her son had
a hidden eagerness that he might be able to find shelter under the
roof of the spice-merchant's son. It was to that motive that 'Don
Alonzo' owed the easy settlement of his agreement with his new
young partner, and not, as he imagined, to the promising air of
luxurious comfort in his surroundings. That offered more allurements
to a third party to the affair.
Don threatened for a few minutes to upset the amiable arrangements
between his real owner and his self-adopted master, for poor Don
had very faint notions of the rights of property and ownership, and
Don was thirsty and Don was hungry, and, moreover, Don was as
fond of grapes as any Christian Don, real or pretended, to be found
in or out of Spain. All of a sudden, while Montoro was gazing
thoughtfully out at the silver line of distant sea, and Don Alonzo was
muttering to himself the remark mentioned above, tired Don caught
sight of a piled-up dish of grapes on a table in the verandah. He
licked his dry lips, and went on eyeing them. Then he licked his dry
lips again, and ventured upon a small whine. That sound recalled
Montoro's wandering wits so far that he turned round and nodded to
his four-footed friend, and said dreamily—
"Yes, yes. All right, good old Don."
That was enough. Don was in that state of longing that a very small
amount of encouragement was enough to induce him to help himself
to the desired feast, and before either of his companions knew well
what he was about, he had bounded up to the table, scrunched up
one juicy, deliciously refreshing bunch of grapes, and had a second
in his mouth about to be treated in the same way. But "there's many
a slip 'twixt the cup and the lip," and in this instance there proved to
be a slip 'twixt the lip and the throat.
Don Alonzo quickly became aware of what was going on, and,
seizing a heavy bottle, he flung it with full force angrily at the dog;
and it hit, not the dog, but the dog's champion, happily only a touch,
and then fell crashing on the floor of the verandah.
The next instant Montoro's first dash forward to save the dog was
followed by a second to save Don Alonzo; for the huge animal had
made a furious spring at his antagonist, accompanied by a growl that
gave full promise of his intentions. Montoro's most resolute and stern
command was needed before the hound was brought to crouch
down by his side, with red-lit eyes still glaring at his unrecognized
owner.
"That brute shall be shot before he's an hour older," came the surly
declaration at last, as Montoro knelt on the stone pavement soothing
the animal back into good temper. At the sharp announcement he
looked up quickly.
"Then you shall shoot him through me," he said passionately, "as
you struck me just now instead of him. He is my only friend out here,
and we will live or die together."
Don Alonzo shook himself irritably. He was good-hearted enough if
over-indulgent parents in the first instance, and superabundant good
fortune since, had not rather spoilt him. Besides, four years' sojourn
on the island of Hispaniola had not tended to teach regard for any
life but his own; that he esteemed at quite a high enough rate, and
he answered Montoro now with angry remonstrance—
"It is all very fine to talk heroics, youngster; but thinkest thou that I
am going to be browbeaten into keeping my own dog, to stand in
danger of being mauled by it any time its tempers up, as if I were a
wretched native!"
Montoro stood up and folded his arms.
"Neither you nor any other man, Indian or European, shall suffer
from Doffs teeth. Or, if perchance that sounds too proud a boast, for
the first human being that Don injures he shall die. He shall be as a
lamb to you now—see—hold out your hand."
With some scarcely-disguised trepidation Alonzo obeyed. Don cast a
beseeching glance of remonstrance at his friend; but instead of any
encouragement to rejection of the offered fellowship, he got a grave
shake of the head; and with a very crestfallen aspect he rose,
walked dolefully along the verandah, and put his paw into the
outstretched hand, and looked up with mute appeal for forgiveness.
Don Alonzo was wise enough to seal the new compact with a freely-
generous gift of more of the coveted grapes. If Montoro for Don, and
Don for himself, would engage that Don Alonzo should never feel the
sharpness of that animal's teeth, his owner was only too willing that it
should live. For it was quite the fashion now to use these powerful
dogs out in the new world, not only as terrible aids in battle against
the poor, half-defenceless Indians, but also to hunt down the
miserable, wholly-defenceless slaves who sometimes dared to run
away to die in peace in their native forests, instead of beneath the
short-sighted, as well as brutal, taskmaster's lash.
The young Diego had declared that Don should never be so
employed, but that declaration Don Alonzo comfortably decided in
his own mind was all nonsense. He himself had had qualms about
the treatment of the natives when he first came out, but he had long
since got rid of all such inconvenient scruples; and so of course
would this new arrival get speedily rid of his. Every one did, with the
exception of that impracticable idiot of a neighbour of his, that young
fellow Las Casas, who had come out from Spain with his head so full
of theories and bookish ideas that he had no room in it for common
sense.
CHAPTER XVII.
GOOD OLD DON.
Time passed on. In Spain good Queen Isabella died, and two years
later the poor, neglected noble-hearted, pious old Admiral,
Christopher Columbus, recommending himself to God, and his two
sons, Diego and Ferdinand, to King Ferdinand's tardy justice and
each other's brotherly love, also bade a final farewell to an ungrateful
world.
And in Hispaniola also time passed on. Many there grieved over the
Admiral when he was dead, who had tormented him in every
possible way when living,—that is the way with poor, stupid human
nature. But he had one true mourner, who had loved and served him
with all his heart during the year that they were together, and whose
memory for those he cared for was not a short one. Montoro de
Diego, amidst his many new interests, felt a very keen pang of
sorrow when the news was brought out to the island, towards the
end of the year 1506, of the loss the world had sustained.
"Ah! Señor Las Casas," he sighed one morning, some months later;
"ah! then, if he had lived, and the queen, you might then have had
hope even yet to work some good for these wretched, rightful
owners of these lands. But now—"
"Ay, indeed!" exclaimed Bartholomew Las Casas with heaving chest,
as he rose and strode hastily up and down his terrace. "You may well
pause upon that but now, Diego. For now one might more wisely
waste breath in calling upon wolves and wild cats to cease from
fierceness, than in pleading with one's fellow-men for mercy, justice,
or compassion. 'Give us yourselves,' is the fierce cry that echoes all
around us. 'Give us yourselves, your wives and daughters, for our
humble slaves; give us your gold, your lands, all you hold most
valuable; resign your wills, your faith, your souls into our keeping,
and we will give you leave to live as long as unremitting toil and
cruelty will let you. But resist us, fight for your country or your liberty,
contradict our lightest caprice, and we will shoot you down as though
you were so many rabbits, we will hunt you to death with our dogs as
though you were vermin or wild beasts.'"
The young man came to a sudden stop, with a face glowing with
generous indignation, and literally panting for breath with his burst of
righteous wrath. Montoro's cheeks were flushed with sympathy as he
said in quick reply—
"It is so. I can but too terribly vouch for the truth of your bitter
accusation. But, Señor, your brethren the priests, can they not—"
Las Casas turned upon him with sharp interruption.
"Can they not help me, you would ask? Ay, verily," with indignant
scorn; "well indeed do they help the cause I have at heart! This is
one of the proclamations allowed by some of those same brethren
the priests—'Your souls are doomed to eternal perdition, your bodies
belong to those who have conquered your soil!' Much good my
brethren the priests will do!"
There was a short silence, and then he continued more calmly, and
laying his hand upon a pile of papers, "But after all, Diego, I do hope
to work some good for the poor natives. I have written out a strong
case for them, and I am intending to return to Spain shortly, there to
plead their cause myself."
"And you shall have my testimony, if you will," said Montoro eagerly.
"For it is our Don Alonzo's will that I should take a journey to Spain
this coming season, in charge of a somewhat richer freight than
usual. And if you start not immediately we may go together."
"And Don?" said Las Casas, in smiling interrogation.
"Ay, truly," was the laughing answer, although something of a blush
accompanied it. "But in faith," he added the next moment, "it is not
only for love of the animal that I have it for my constant companion.
Since I have discovered the horrible use to which its fellows are put,
I live in fear of a coming day when I may regret having saved its life."
"Then," continued his friend, "you will leave it behind you in Spain
perchance, when you return hither?"
"That is so long to look ahead," said Montoro, feeling not a little glad
that he was not called upon for an immediate decision.
When it really came to the point he did what he thought much better
than leaving Don behind in El Cuevo. He got Master Pedro to
transfer all property in it to himself. His services to the old spice-
dealer and his son had well merited so much of a reward. And as for
Don, he deserved not only a good master, but almost as many
bunches of grapes besides as he chose to eat, when, a couple of
years later, he was the means of saving Montoro's life and a bag full
of gold-dust to the value of many thousand pesos.
Diego's first return journey to Spain proved so successful, owing to
his scrupulous honesty and intelligence, that Don Alonzo speedily
sent him on a second, and others also most eagerly availed
themselves of so upright a messenger to transmit their golden
gleanings to their own country.
But, as it happened, with Diego there voyaged also to Spain three
ne'er-do-wells. They had gambled away all their slaves, all their
grants of land, all their gathered-up spoils, and then, having finally
gambled away all their future prospects of wealth in Hispaniola, the
miscreants, as mean as they were bad, slipped away from the island
and their creditors on the first ship back to Spain.
"And mind ye," muttered one of the number to his companions one
evening, as they drew near the end of their two months' voyage,
—"mind ye, if we follow that insolent, set-up fellow Diego a day or
two's journey up the country after landing, we shall not be losing
time, neither shall we have cause to regret having left Hispaniola in
his company."
"How so?" questioned one of the two eager listeners doubtfully. "My
child yonder, little Bautista, told me when I questioned him some
days ago anent Diego's gold, that the bags were to be sent by other
hands to Madrid."
"And you credit the tale!" exclaimed the first speaker scornfully.
"You'll believe next that the Garden of Paradise has been found."
"And so I will," was the retort, "when the news is given me by
Montoro de Diego. He would not lie to save his life, and least of all
would he lie to a child."
"By all the saints," sneered the third of the group, "but Don Diego
hath a warm advocate in you! Doubtless it were useless to expect
you to touch his gold, even though it lay by the wayside to be picked
up."
"Doubtless under those circumstances," was the sharp reply, "there
should be little left for you to snatch. All the same, he hath shown
kindness to my boy, and he tells him nought but truth."
"Well, well," said Almado, the first speaker, more softly, "there is no
need that we should wrangle over the fellow's virtues, they sicken
me forsooth. Ne'er the less, he shall be a very saint if you will, so we
do but get his merchandise. As for the gold that is to go to Madrid,
that is but that small part, of what he carries, which is for the king's
coffers. Of that I am well assured. So you see thy little son yonder
hath been told the truth indeed, but only in part, and maybe to
mislead us."
"Umph," muttered Bautista's father, also more quietly. "That may well
be."
"Ay," agreed the third of the company, "that may well be."
And for the next few hours they all redoubled their efforts to be on
good terms with Don. They flattered themselves, indeed, that he
regarded them quite in the light of friends, for Don, like most very
strong creatures, whether going on two legs or four, never troubled
himself to show uncalled-for fierceness. As long as no one interfered
with him or his master, and his master gave him no orders to
interfere with others, he maintained the grave indifference of manner
worthy of a highborn Spaniard. But woe betide those who should
presume upon this calmness.
Arrived at Cadiz, Montoro delivered up the royal revenue to the
authorized messengers awaiting it, and then he and his dog and his
bags set out on their journey up the country, in company with worthy
Master Sancho, who had come to meet him, and two or three other
traders from the interior.
"Farewell, my little Bautista," said Montoro; "I shall pray for our future
meeting."
"Nay," said the child hurriedly, and with a frightened look round, "do
not that, Señor. I love you, you have been good to me, and so I pray
the Virgin to grant we may not meet again."
Montoro opened his eyes wide.
"How so, little man? Love me, and yet pray that we may not again
cross each other's paths? How is that, tell me?"
But the boy shook his head, and began to tremble violently.
"Do not ask me," he muttered with white lips; "they will kill me. Only
keep away from us. They do not know I have heard——"
"Ha!" exclaimed Montoro, a look of intelligence now taking the place
of bewilderment. Then he stooped and kissed the child's forehead,
as he said in low tones, "Blessings on thee for thy true heart, my little
lad, and my thanks. May the Lord have thee in His keeping, and
guard thy hands from sin."
And so they parted, each, as poor little Bautista fondly thought, to go
widely different ways, but in reality to take two routes leading to the
same goal.
For the first two days' journey inland the party to which Montoro
joined himself was a particularly strong one, too strong for the three
gamblers to care to meddle with; accordingly they withdrew
themselves from notice, until the travelling company was reduced to
Montoro himself, Master Sancho and his thick-headed attendant,
and a couple of poor-spirited merchants, who would have rather
hidden themselves in their bales at the appearance of danger, than
tried to defend them. But then—there was Don.
The third day was drawing to a close, when Diego and his
companions reached a wretched little inn, the worst on their route,
and with considerable grumbling on the part of comfort-loving Master
Sancho, they put up there for the night. To make matters worse, the
amount of available accommodation was even less than usual, for
another party of travellers had arrived before them, and taken the
chief and largest room.
However, there was no help for it. Master Sancho had to make the
best of a bad bargain, and as nothing would induce him to share a
room with Don, and nothing would induce Montoro to dispense with
Don's company as a guardian under present circumstances, he and
the dog had one room, and the worthy burgess of El Cuevo and the
two merchants from Saragossa had to crowd into the other.
"One night," explained Master Sancho to his companions, "that
young rascal I've taken a fancy to, persuaded me to share a sleeping
apartment with him and that great brute, and in the night I snored,—
I'm given to snore,—and the creature didn't approve, and woke me
up with a sounding thump of its great paw. And there, behold! it
stood reared up over me, with glaring eyes and a growling mouth. I
warrant you, I prayed in one minute to more saints in the calendar
than I've prayed to in many a long year before."
"Doubtless," assented one of the merchants with paling cheeks. "I
have ever thought it a fearful great beast, and unsafe. But hearken!
Methinks it is now quarrelling even with its own master. Ah!" with
startled breathlessness—"it is shot."
Then there was a sudden rushing all over the inn. Screams, shrieks,
shouts, slamming of doors, and above all, the continuous roar of
Don's deep growling bark.
At length men and lights were gathered in Montoro's room, and there
stood Montoro holding in a firm grip one of the smugglers. But the
hero of the fray, and the conqueror, was grand old Don standing with
one great fore-paw on the breast of one robber, the other fore-paw
on the breast of Bautista's father, who lay weltering in his blood, shot
by the other of his comrades in the attempt to shoot the dog.
"But my child, my little son," murmured the wretched, dying man.
"I will guard and care for him," said Montoro huskily.
He had been rescued from misery himself once, now he was the
rescuer.
CHAPTER XVIII.
DEATH FOR DON.
It was the early part of the year 1511, when Montoro, become now
quite an experienced islander and man of business, left Don
Alonzo's place, Palmyra, one morning for the neighbouring town of
San Domingo. The object of the visit was to arrange some important
matters with certain foreign merchants, who had lately arrived with
tempting offers to the planters for the produce of their estates.
"And don't hurry thyself," said Don Alonzo with unusual
consideration. "Take thy pleasure for a few days when thou art in the
town, for verily this dog's hole of a place is dull enough to make a
man long to shuffle off life with a native's readiness."
"If those same natives should get the upper-hand," answered
Montoro drily, "I doubt not they would help you. Meantime, I will trust
to find you still in the flesh, and well, when I return, and so—adios."
"And for you, fair journeyings and good bargains," said the indolent
superior, as he lay lounging in his low chair sipping a cool lime-juice
beverage. Little enough of the work he did himself towards
accumulating his own wealth.
But, lazy and self-indulgent as he was, it had not escaped Montoro
that there was a certain scarcely-suppressed eagerness, and barely-
hidden hope of some sort, underlying his present declared wishes for
his subordinate's comfort. As Montoro left the verandah and passed
through the house he called to his rescued protégé, who had proved
useful enough to secure himself a home beneath Don Alonzo's roof.
No work had seemed to come amiss to him, excepting that of aid to
the overseers in the gold mines, in which he had been recently
employed. But the brutal task-masters had just sent the boy back,
saying that he was no good to them whatever, worse than no good
indeed, for he pitied the rascally workers instead of flogging them.
Bautista came readily enough when he heard his beloved Señor
Diego's voice.
"Am I to go with you, my Señor?" he exclaimed beseechingly. "Ah!
but I will be to you eyes and hands and feet, if I may."
"I prefer to use my own, thank you," answered Montoro smiling, as
he patted the boy's head. "But look not so disappointed, Bautista, for
if I cannot trust myself to thee, I am going to leave in thy charge one
I hold almost dearer. I leave thee guardian of our faithful old Don.
And see thou that he comes to no harm, and—that he does no harm.
I have guarded him from that sin hitherto; do thou guard him in my
absence."
A deep breath, almost a groan, burst from the boy's lips.
"My Señor," he muttered anxiously, "give me some other duty to
perform for you. This may be too hard."
Diego frowned.
"I trust not," he said sternly. "It shall be worse for others if it prove so.
And remember, you have my orders, and if need be you must
declare them."
So saying he nodded his farewell to the boy and departed, leaving
Don's new guardian in a very doleful frame of mind, for he knew well
enough the cause of Don Alonzo's desire to be a short time rid of
Montoro.
The spice-merchant's son was good-natured enough so long as he
was crossed in nothing, but Montoro's settled refusal to have Don
used as a hunter of runaway slaves had roused Alonzo's spite, and
for the past year, ever since the return of Montoro and the dog from
Spain, he had been seeking some chance to gratify his malice.
Hitherto where Diego had gone the dog had gone, but at last this
expedition to the town was arranged, and for various circumstances
it was more convenient to leave Don behind.
"And at last," declared Don Alonzo with a malicious chuckle, "at last
the brute shall be set to its proper work."
Bautista was in the apartment at the time, as well as one of the
overseers, and as a significant warning to him the words were added
—"And it shall have its first taste of the flesh of any one, be he
Spaniard or native, who betrays my purpose to Señor Long-face."
No wonder the boy desired that some other duty might be commuted
to his charge by his patron, in test of his affection. As Montoro rode
off with a party of attendants, Bautista made his way to Don, and
poured out his fears to an apparently perfectly intelligent pair of ears.
"But all the same, you know quite well, Don," said Bautista
reproachfully, "you do know quite well, that in spite of your good
Christian bringing up, you would seize a poor redskin by the leg if
you were set at him."
"Of course he would, like the sensible thoroughbred he is," shouted
a well-known voice not a couple of yards distant. And Bautista
sprang to his feet with a terrified look on his face, as he saw the
hateful head overseer, Jerome Tivoli, had come up to him
unperceived.
The man now stood intently regarding the dog, with a more sinister
expression than usual upon his cruel face, and the boy could
scarcely restrain himself from flying away from the spot. Nothing
short of his loyal devotion to his patron could have kept him there. At
last he said huskily—
"It is useless so to examine this dog, for, strong or weak, you can
have nought to do with it, since it belongs to the Señor Diego, and he
chooses not that it should be used for your purposes."
De Tivoli uttered a short, hard laugh, and his eyes glittered as he
said slowly—
"Ah! yes. It is the Señor Montoro de Diego's dog—-his favourite. And
verily it is a fine animal, and powerful, and will do a day's work well
for us. That dog of a slave Guatchi has run away, and, dead or alive,
yon pet of our Señor Diego shall bring him back to us."
Bautista flung himself down again beside the dog, and threw his
arms about its neck, as he exclaimed with the courage of affection—
"No! I tell thee no, Señor Tivoli. Señor Diego has left it to me to
guard his dog from doing harm, and I will keep my charge."
De Tivoli's thin lips curled; but ere he could reply other footsteps
were heard approaching, and Don Alonzo himself appeared upon
the scene.
"How now, De Tivoli," he exclaimed hastily. "Why dost thou waste
time? The idle rascal Guatchi hath had start enough, I trow, to
breathe the dog e'en now; why dost thou delay?"
"It is but for a minute, Don Alonzo," replied the other coolly. "Yon boy
declares that, for Don Diego's sake, it shall not be sent hunting."
"And I," retorted Don Alonzo, "swear by St. Jago that it shall."
"And I, in the name of one higher," exclaimed Montoro de Diego,
thus unexpectedly making his own appearance on the scene again,
"I declare, with Bautista, that it shall not go."
Don Alonzo started slightly, and his face flushed for a moment with
ill-restrained annoyance and uneasiness as he saw that set, resolute
countenance before him; but he tried to assume an air of
carelessness, and to laugh away the matter with an off-hand—
"Why, my mentor, how have you contrived to accomplish the
business you had in hand so quickly? What brings you back so
soon?"
"Your good genius, I feel inclined to imagine," was Montoro's answer,
in tones somewhat quieter than those of his first exclamation. But the
fading sparkle in his eyes rekindled as his companion replied irritably
—
"Then I wish the meddlesome beast had minded its own business,
instead of sending you back here to pull a long face over what I
mean to do in spite of it."
As he spoke he walked up to where the dog Don lay tethered, held a
strip of cotton cloth to its nose, and then muttering viciously—
"Find him, Don, find him!" pressed his finger hastily on the spring of
the dog's collar, and set it free.
The great animal bounded forward. The next instant there was a
howl, a moan, and Don lay dying at Montoro's feet; rather, one
should say, at Montoro's knees, for the young man had sunk on to
them almost as soon as his own fist had fallen with that lightning
stroke, and the same hand that had dealt the death-blow was now
soothing the poor brute's last agonies. It was Montoro de Diego who
had killed it, and yet it was to Montoro's face that the pleading brown
eyes were lifted with their last gaze of affection, and it was Montoro's
hand that the dying tongue licked with the last breath.
"My poor old Don," muttered Montoro huskily, as he tenderly pressed
the side quivering with the death struggle; "poor old Don."
"It's fine for thee to pity the poor brute when it owes its sufferings to
thy malice," exclaimed Don Alonzo furiously, and with fingers on the
hilt of his dagger, as though they itched to lay his companion beside
the animal.
But Diego paid no seeming heed to the show of rage. Maintaining his
kneeling position for a while longer, he replied quietly—
"Yes, it once owed its life to me, and now it owes its death to me,
and better so than it should have been the innocent cause of
suffering to one of our human brethren, for whom the cross rose on
Calvary."
And then he rose from beside the dog's dead body, and turned
slowly away with a saddened face. In spite of its ferocious nature,
the animal had always been most docile with him; and besides, it
had been that oft-felt link with his mother's home. How long ago now
seemed that first day of parting from his country, when Rachel de
Diego's slender fingers had rested for a few moments on the
animal's head. Her son would far rather have a second time
undergone some peril to save its life, than have had to destroy it for
the prevention of a crime.
"Ah, Señor," murmured Bautista, as he crept out on to the verandah
after him a few minutes later. "Ah, Señor, you have saved poor
Guatchi's limbs from being mangled; but I doubt me you have made
an enemy for yourself."
"You were willing to do the same in the same cause, Bautista," was
the answer with a grave smile of approval. "I knew not that thou wast
so staunchly ranged on the side of justice and mercy. Henceforth we
are friends."
The boy sprang forward to clasp the hand held out to him, and said
eagerly—
"To follow in your steps, Señor, I began to remind myself that the
Indians' flesh had feelings like our own, but my past month in the
mines has been a black lesson in horror that I would not repeat to
escape the pains of purgatory. These Indians are tenfold weaker
than we are, and their sufferings are tenfold more, for they have
learnt nothing of manhood to sustain them. You have seen them die
here in the plantations, Señor, and that has roused your pity; but in
those mines it is not that some die, but that none survive. A few days
of that dismal work beneath cuffs and lashes, and their strength is
spent—"
"And then?" came the short query.
"And then," ended the boy with a sort of gasp for breath, "they sink to
the ground, and the brutal kick given to rouse them up to continued
labour, is the accompaniment of their last breath. It is little wonder,
Señor, that I should wish poor Guatchi to get away free, now that he
has escaped such toil alive."
The whole fervour of the boy's susceptible nature was aroused, and
Montoro felt more than ever convinced that he was in the presence
of one whose spirit was akin to his own.
"Hearken, Bautista," he said, after a short pause. "I have within the
past few hours copied out part of a commission against the
miserable inhabitants of this new world, lately granted by our king,
and framed by the greatest divines and lawyers of our old home.
Alonso de Ojeda and Diego de Nicuessa bear drafts of this
commission with them, and be well assured that they will not spare
its execution. But stay; I will read thee the very words themselves,
addressed for peremptory orders to these poor heathen, ignorant of
the very language in which we call upon them to obey our faith and
laws:—'If you will not consent to take our Church for your Church,
the holy father the Pope for your spiritual head, our king for your king
and sovereign lord over your kings and countries, then, with the help
of God, I will enter your country by force; I will carry on war against
you with the utmost violence; I will subject you to the yoke of
obedience; I will take your wives and children and will make them
slaves; I will seize your goods, and do you all the mischief in my
power, as rebellious subjects, who will not submit to their lawful
sovereign. And I protest that all the bloodshed and calamities that
shall follow shall be due to you, and not to us.'"[2]
As Montoro came to the end of his sheet he folded and replaced it in
his pocket, and then, utterly forgetful of his companion in his
reawakened indignation, he wandered away from the verandah, and
betook himself to the simple dwelling of the good clerigo,
Bartholomew de las Casas, who was now finally settled in
Hispaniola, by royal desire, as a missionary to the natives.
"But of what use," he exclaimed this afternoon in sorrowful despair to
his equally weary-hearted visitor, "of what use, Diego, to waste our
time and strength, in trying to teach the sublime truths of religion to
men whose spirits are broken, and their minds weakened by
oppression?"
"Of what use, indeed," assented Montoro with passion, "to try to
teach men to believe in a religion professing itself the religion of love
and mercy, while they are slaves to those calling themselves its
followers, and who are acting at the same time the part of demons!"
"You speak strongly," said the true-hearted, good Christian bishop.
"But verily I cannot say you have not reason. Knowest thou, my
friend, that when first we settled ourselves upon this fertile fragrant
island, not yet fifteen years ago, the inhabitants numbered above
three millions, and now they scarcely amount to fifteen thousand.
Scarcely fifteen thousand!" he repeated slowly, and in awe-struck
tones, as though he scarcely could endure to recall the awful fact to
his own remembrance.
Welcome to our website – the ideal destination for book lovers and
knowledge seekers. With a mission to inspire endlessly, we offer a
vast collection of books, ranging from classic literary works to
specialized publications, self-development books, and children's
literature. Each book is a new journey of discovery, expanding
knowledge and enriching the soul of the reade
Our website is not just a platform for buying books, but a bridge
connecting readers to the timeless values of culture and wisdom. With
an elegant, user-friendly interface and an intelligent search system,
we are committed to providing a quick and convenient shopping
experience. Additionally, our special promotions and home delivery
services ensure that you save time and fully enjoy the joy of reading.
ebooknice.com